home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Assassins - Ultimate CD Games Collection 4
/
Assassins 4 (1999)(Weird Science).iso
/
workbench_games2
/
mines_sweeper
/
mines.asm
< prev
next >
Wrap
Assembly Source File
|
1998-03-21
|
148KB
|
6,374 lines
;************************************
;* MINESWEEPER *
;************************************
;by Andry of PEGAS
;$VER: Source code for MineSweeper V0.76 by PEGAS (15.6.97)
;Feel free to use this source, but give me credits AT LEAST.
V='V'
E='0'
R='.'
S='7'
I='6'
MACHINE MC68020
;To do:
; + MinWin_Left, MinWin_Top
; - scale sun and numbers
; + all system calls: arguments to LONG, (+) base adr. to a6!!!
; + Use semaphores instead of Forbid()/Permit()
; + Be sure that comparsions on addresses are unsigned!!
; + Check functions for ALL possible returncodes. If possible r-codes
; are A, B or C, do not assume that C if not (A or B).
; - Try to understand and use memory pools.
; - first create AppIcon (AppMenu) before closing the window (if fails...)
; + LOAD/SAVE - if read/writebytes != expected then FAIL
; + check MEMF_PUBLIC
; + check return of ItemAddress
; - adjust preferences
; - u preferenci (adjust) pridelat ke "screen size" GUESS
; - version (.doc, $VER: , title (win/scr), about, source)
; - udelat z .doc .guide
INCLUDE "SOURCES:mines/mines.i"
TRAPRMB MACRO
ori.l #WFLG_RMBTRAP,([MyWindow],wd_Flags)
ENDM
FREERMB MACRO
andi.l #~WFLG_RMBTRAP,([MyWindow],wd_Flags)
ENDM
;*********************************************************************************
SECTION MineSweeper,CODE
jmp _IconStart
_main
lea (EB,PC),a0
move.l 4.w,(a0)
bsr.w CallOtherSweeper ;also inits semaphore structure
;**clear the whole bss section
lea BssStart,a0
lea BssEnd,a1
.clrbss clr.l (a0)+
cmpa.l a0,a1
bne.s .clrbss
move.l #Allocated,AllocPos
;**Open some libraries first
bsr.w OpenReqTools ;open this at first!!
beq.w noReqTools
;processor check (68020+)
movea.l (EB,PC),a6
btst.b #AFB_68020,(AttnFlags+1,a6) ;MC_68020?
bne.s .mcok ;yes
lea oldproc_Text,a1
lea oldproc_Button,a2
bsr.w InformationReq
bra.w oldProcessor
;kickstart 3.0+ check (V39+)
.mcok cmpi.w #39,(LIB_VERSION,a6)
bhs.s .ksok
lea oldks_Text,a1
lea oldks_Button,a2
bsr.w InformationReq
bra.w oldKickstart
.ksok
bsr.w OpenPublicPort
tst.l (MinesMsgPort,pc)
bne.s .ppok
lea nopubport_Text,a1
lea nopubport_Button,a2
bsr.w InformationReq
bra.w noPublicPort
.ppok ;**open "timer.device"
movea.l (EB,PC),a6
jsr (_LVOCreateMsgPort,a6) ;MsgPort
move.l d0,TimPort
beq.w error_NoTimerDevice
movea.l d0,a0 ;replyport
move.l #IOTV_SIZE,d0 ;size
jsr (_LVOCreateIORequest,a6) ;IORequest
move.l d0,TimIoReq
bne.s .ioreqok
.deletemsgport movea.l TimPort,a0 ;delete MsgPort <=> IORequest=0
jsr (_LVODeleteMsgPort,a6)
bra.w error_NoTimerDevice
.ioreqok movea.l d0,a1 ;IORequest
move.l #UNIT_VBLANK,d0
moveq #0,d1
lea TimDevName,a0
jsr (_LVOOpenDevice,a6) ;OpenDevice
tst.l d0
beq.s .timdevok
movea.l TimIoReq,a0
jsr (_LVODeleteIORequest,a6)
bra.s .deletemsgport
.timdevok movea.l TimIoReq,a0
move.l (IO_DEVICE,a0),TimDevBase
.devok bsr.w OpenIntuition ;some libraries
beq.w noIntuition
bsr.w OpenGraphics
beq.w noGraphics
bsr.w OpenDos
beq.w noDos
bsr.w OpenGadtools
beq.w noGadtools
bsr.w OpenUtility
beq.w noUtility
bsr.w GetOutput
;**copy default palette to screen palette
lea DefaultPalette,a0
lea ScreenPalette,a1
moveq #PALENTRIES*3+2-1,d0
.loop move.l (a0)+,(a1)+
dbra d0,.loop
;**Get preferences
bsr.w GetStartDirs ;get lock of start directory and go there
bsr.w LoadPreferences
tst.l MyPrefs ;this MUST be valid
beq.w exit_noprefs
bsr.w LoadHiScores
bsr.w OpenFont ;open prefered font
bsr.w FontToRT ;set font to reqtools tags
iconify_Return
;**Open screen (If set in prefs)
bsr.w OpenMyScreen
bsr.w LockScreen
tst.l MyScreen
beq.w error_NoScreen
bsr.w GetDRI ;get DrawInfo
bsr.w SetPalette ;set colors
bsr.w GetButtonSizes ;get size of buttons
;-set mimum of fields per row
move.l #MINBARWIDTH,d0
divu.w ButtWidth,d0
bfclr d0{0:16}
beq.s .noadd
addq.w #1,d0
.noadd move.w d0,MinRowBut
bsr.w GetVisualInfo
tst.l VisualInfo
beq.w error_NoVI
;**create buttons gfx
bsr.w CreateGfx
tst.l MGGfx
beq.w error_noGfx
;**Set window parameters
bsr.w GetScreenCenter
bsr.w SetWinParams ;due to MyPrefs
bsr.w SetWinTagList
bsr.w SetZoomParams
bsr.w OpenMyWindow
tst.l MyWindow
beq.w noWindow
;**SetMenu
bsr.w SetMenu ;completely sets menu strip
move.l #IDCMPFLAGS,d0
tst.l MenuStruct
beq.s .0 ;No menu
or.l #IDCMP_MENUPICK,d0
.0 bsr.w ChangeIDCMP
tst.l ([MyWindow],wd_UserPort) ;IDCMP allocated?
bne.s .idcmpok
lea noidcmp_Text,a1
lea noidcmp_Button,a2
bsr.w InformationReq
bra.w noIDCMP
.idcmpok tst.b DisplayTooBig
beq.s .skip2
lea toobig_Text,a1
lea toobig_Button,a2
bsr.w InformationReq
clr.b DisplayTooBig
.skip2
bsr.w AddGadget ;add sun gadget
move.l GadtoolsBase,a6
movea.l MyWindow,a0
suba.l a1,a1
jsr (_LVOGT_RefreshWindow,a6) ;hmmm...they tell to do this..
bsr.w CheckShowXmas
;uniconifying?
tst.b FromIconify
beq.s .notic
clr.b FromIconify
bsr.w PutAllToFront
tst.b Play ;were you playing?
beq.s .nottofront ;no
move.b #RW_ACTUAL,d0
bsr.w RedrawWindow
bsr.w StartTimer
bra.s .skipinit
.notic
tst.b ([MyPrefs],mprf_WActivate)
bne.s .nottofront
movea.l IntuiBase,a6
movea.l MyScreen,a0
jsr (_LVOScreenToFront,a6)
.nottofront
;**alloc and init PF
bsr.w InitBeforeStart
tst.l PFAdr
beq.w ExitSweeper
.skipinit
clr.b FromIconify
;***Main loop*******************************************************
;**Don't forget the Disable,Pause flags!!!!!!!!!!
;get signal bits of both ports
movea.l MyWindow,a0
movea.l (wd_UserPort,a0),a0
move.b (MP_SIGBIT,a0),d0
move.b d0,WinPortSigBit
moveq #0,d1
bset d0,d1
movea.l (MinesMsgPort,pc),a0
move.b (MP_SIGBIT,a0),d0
move.b d0,PubPortSigBit
bset d0,d1
move.l d1,SignalBits
MainLoop
;wait for signals from both ports
movea.l (EB,PC),a6
move.l SignalBits,d0
jsr (_LVOWait,a6)
move.b WinPortSigBit,d1 ;wd_UserPort?
btst d1,d0
bne.s CollectLoop ;yes
;else MineSweeper public port
.collect movea.l (EB,PC),a6
movea.l (MinesMsgPort,pc),a0
jsr (_LVOGetMsg,a6)
tst.l d0
beq.s MainLoop ;no more messages
movea.l d0,a1
move.l (am_ID,a1),d2
jsr (_LVOReplyMsg,a6)
cmpi.l #'MINE',d2
bne.s .collect
;ok a new MineSweeper was started. That means, bring my window to front
;and activate.
bsr.w PutAllToFront
bra.s .collect
CollectLoop
movea.l MyWindow,a2
movea.l GadtoolsBase,a6
movea.l (wd_UserPort,a2),a0
jsr (_LVOGT_GetIMsg,a6)
tst.l d0 ;just message for gadtools?
beq.s MainLoop
movea.l d0,a1
;**copy message to my buffer
movea.l d0,a0
lea IntuiMessBuf,a2
moveq #(im_SIZEOF/2)-1,d0
.loop move.w (a0)+,(a2)+
dbra d0,.loop
jsr (_LVOGT_ReplyIMsg,a6) ;message in A1
lea IntuiMessBuf,a0
move.l (im_Class,a0),d0 ;get message
;**Handle message in d0
cmpi.l #IDCMP_CHANGEWINDOW,d0
beq.w HandleNewSize
tst.b IDidTheChange ;still waiting for the window to resize?
bne.s CollectLoop ;yes
cmpi.l #IDCMP_MOUSEMOVE,d0
beq.w HandleMouseMove
cmpi.l #IDCMP_ACTIVEWINDOW,d0
beq.w HandleTimer
cmpi.l #IDCMP_INTUITICKS,d0
beq.w HandleTimer
cmpi.l #IDCMP_MOUSEBUTTONS,d0
beq.w HandleButtons
cmpi.l #IDCMP_GADGETDOWN,d0
beq.w HandleGadgetDown
cmpi.l #IDCMP_GADGETUP,d0
beq.w HandleGadgetUP
cmpi.l #IDCMP_VANILLAKEY,d0
beq.w HandleVanillaKeys
cmpi.l #IDCMP_MENUPICK,d0
beq.w MenuPick
cmpi.l #IDCMP_CLOSEWINDOW,d0
beq.s ExitSweeper
bra.w CollectLoop
;*******************************************************************
ExitSweeper
noIDCMP
bsr.w ClearMenu
bsr.w CloseMyWindow
noWindow
error_noPF
bsr.w FreeGfx
error_noGfx
bsr.w FreeVisualInfo
error_NoVI
bsr.w CloseMyScreen
;check if highscores are saved
movea.l MyPrefs,a0
tst.b (mprf_Warn,a0)
bne.s .dontsave
tst.b (mhs_NewHiscore,a0)
beq.s .dontsave
tst.b (mhs_Valid,a0)
beq.s .dontsave
bsr.w mh_HiScores
.dontsave
error_NoScreen
bsr.w CloseFont
exit_noprefs
bsr.w FreeStartDir
movea.l (EB,PC),a6
movea.l UtilityBase,a1
jsr (_LVOCloseLibrary,a6)
noUtility movea.l (EB,PC),a6
movea.l GadtoolsBase,a1
jsr (_LVOCloseLibrary,a6)
noGadtools
noDos movea.l (EB,PC),a6
movea.l _GfxBase,a1
jsr (_LVOCloseLibrary,a6)
noGraphics movea.l (EB,PC),a6
movea.l IntuiBase,a1
jsr (_LVOCloseLibrary,a6)
noIntuition movea.l (EB,PC),a6
movea.l TimIoReq,a1
jsr (_LVOCloseDevice,a6)
movea.l TimIoReq,a0
jsr (_LVODeleteIORequest,a6)
movea.l TimPort,a0
jsr (_LVODeleteMsgPort,a6)
noTimer bsr.w ClosePublicPort
noPublicPort
oldKickstart
oldProcessor movea.l (EB,PC),a6
movea.l _ReqToolsBase,a1
jsr (_LVOCloseLibrary,a6)
noReqTools
move.l DosBase,d2
beq.s .nodos
move.l (MyOut,pc),d1 ;get my output file
beq.s .noout ;exist?
movea.l d2,a6
jsr (_LVOClose,a6) ;close it
tst.l d0
bne.s .noout ;closed succesfully
lea notclosed_Text,a0
bsr.w PrintText
.noout
movea.l (EB,PC),a6
movea.l d2,a1
jsr (_LVOCloseLibrary,a6)
.nodos
bsr.w FreeAllMemory
bsr.w FreeSemaphore
moveq #0,d0
rts
error_NoTimerDevice
lea notimd_Text,a1
lea notimd_Button,a2
bsr.w InformationReq
bra.s noTimer
;*******************************************************************
MenuPick move.w (im_Code,a0),d2
;**Search for matching code
MenuSearch cmpi.w #MENUNULL,d2
beq.w mp_Exit
st HandleNext ;flag
lea MyMenu,a2
.loop cmpi.b #NM_END,(mmi_Type,a2)
beq.s mp_Exit
cmp.w (mmi_Code,a2),d2
beq.s .match
lea (mmi_SIZEOF,a2),a2
bra.s .loop
.match move.l (mmi_Handler,a2),d0 ;check for handler
beq.s mp_Skip ;no handler
movea.l d0,a0 ;is there any?
movem.l d2/a2,-(sp)
jsr (a0) ;skip to a handler
movem.l (sp)+,d2/a2
mp_Skip tst.b HandleNext
beq.s mp_Exit
movea.l IntuiBase,a6
movea.l MenuStruct,a0
move.l d2,d0
jsr (_LVOItemAddress,a6)
movea.l d0,a0
move.w (mi_NextSelect,a0),d2
bra.s MenuSearch
mp_Exit bra.w CollectLoop
;******************************************************************
FLAG =2
QMARK=3
HandleButtons clr.b SunPressedOnce ;interrupt double clicking
movea.l a0,a2
tst.b Disable
bne.w CollectLoop
tst.b Ready
beq.w CollectLoop
tst.b Pause
bne.w CollectLoop
move.w (im_Code,a2),d3
btst #7,d3 ;just an upstroke?
bne.w CollectLoop ;yes
move.w (im_MouseX,a2),d0
move.w (im_MouseY,a2),d1
sub.w MinPFX,d0 ;check range
bmi.w CollectLoop
sub.w MinPFY,d1
bmi.w CollectLoop
cmp.w PFXPix,d0
bhs.w CollectLoop
cmp.w PFYPix,d1
bhs.w CollectLoop
ext.l d0
ext.l d1
divu.w ButtWidth,d0
divu.w ButtHeight,d1
addq.w #1,d0
addq.w #1,d1
move.w d0,LastX
move.w d1,LastY
move.w d1,d2
mulu.w PFWidth,d2
add.w d0,d2 ;button's offset
movea.l PFAdr,a0
adda.w PFSize,a0
cmpi.w #IECODE_LBUTTON,d3
beq.s .lmb
cmpi.w #IECODE_RBUTTON,d3
beq.s .rmb
bra.w CollectLoop
.rmb movea.l MyPrefs,a5
tst.b (mprf_Question,a5) ;QUESTION_MARK=YES?
beq.s .2 ;yes
.1 cmpi.b #FLAG,(a0,d2.w) ;flag?
beq.s .removef ;just remove
bra.s .12skip
.2 cmpi.b #FLAG,(a0,d2.w) ;flag?
beq.s .question ;set qmark
cmpi.b #QMARK,(a0,d2.w)
beq.s .removeq
;neither flag nor qmark
.12skip tst.b (a0,d2.w)
beq.s .notpressed
tst.b (mprf_RMouseGame,a5) ;NORMOUSEGAME?
bne.w .ok ;yes
movea.l PFAdr,a1
tst.b (a1,d2.w) ;pressed-empty button?
beq.w .ok ;yes
;check number of flags around this PRESSED button
movem.w d0/d1,-(sp)
move.w #FLAG,d1 ;item to check
move.w d2,d4 ;offset
move.w PFWidth,d2
bsr.w GetAround
cmp.b (a1,d4.w),d0 ;is num. of flags around equal to the number?
movem.w (sp)+,d0/d1
bne.w .ok ;no
;now uncover all buttons around
bra.s .skipsub
.Uncover ;d0-x d1-y d2-offset
move.w d1,d2
mulu.w PFWidth,d2
add.w d0,d2
movem.w d0-d2,-(sp)
bsr.w ShowButton
cmpi.b #mgg_Bomb/4,d0
movem.w (sp)+,d0-d2
bne.s .uncok
movea.l PFAdr,a0
move.b #mgg_Blowed/4,(a0,d2.w)
move.w #mgg_Blowed/4,d2
movem.w d0/d1,-(sp)
bsr.w PutButton ;show the blowed immediatly
movem.w (sp)+,d0/d1
move.w #-1,(4,sp) ;set loose flag
.uncok
rts
.skipsub clr.w -(sp) ;room for loose-flag
subq.w #1,d0 ;1st line
subq.w #1,d1
bsr.s .Uncover
addq.w #1,d0
bsr.s .Uncover
addq.w #1,d0
bsr.s .Uncover
subq.w #2,d0 ;2nd line
addq.w #1,d1
bsr.s .Uncover
addq.w #2,d0
bsr.s .Uncover
subq.w #2,d0 ;3rd line
addq.w #1,d1
bsr.s .Uncover
addq.w #1,d0
bsr.s .Uncover
addq.w #1,d0
bsr.s .Uncover
tst.w (sp)+ ;loose?
beq.w .ok0
clr.b Win
bra.w .0
.notpressed move.b #FLAG,(a0,d2.w) ;set a Flag
subq.w #1,BCount
move.w #mgg_Flag/4,d2
bsr.w PutButton
bra.w .ok
.question move.b #QMARK,(a0,d2.w) ;set qmark
addq.w #1,BCount
move.w #mgg_Question/4,d2
bsr.w PutButton
bra.s .ok
.removef addq.w #1,BCount
.removeq clr.b (a0,d2.w)
move.w #mgg_Empty/4,d2
bsr.w PutButton ;put a single button
bra.s .ok
.lmb tst.b Play
beq.w .NotPlayingYet
.cont tst.b FirstTime
beq.s .cont1
clr.b FirstTime
movea.l PFAdr,a1
cmpi.b #mgg_Bomb/4,(a1,d2.w)
bne.s .cont1
bsr.w RemoveBomb
.cont1 move.w d2,-(sp)
bsr.w ShowButton
move.w (sp)+,d2
cmpi.b #mgg_Bomb/4,d0 ;found a bomb?
bne.s .ok0
clr.b Win ;you loose
movea.l PFAdr,a0
move.b #mgg_Blowed/4,(a0,d2.w)
move.w LastX,d0
move.w LastY,d1
move.w #mgg_Blowed/4,d2
bsr.w PutButton
bra.s .0
.ok0 tst.w WinCount
seq Win
bne.s .ok
.0 bsr.w EndPlaying
.ok lea (.OldBC,pc),a0 ;redraw number of bombs (if changed)
move.w BCount,d2
cmp.w (a0),d2
beq.s .exit
move.w d2,(a0)
move.w BCountX,d0
move.w BCountY,d1
bsr.w DrawNumber
.exit bra.w CollectLoop
.OldBC dc.w 0
.NotPlayingYet st Play ;now playing
TRAPRMB
movem.w d0-d2,-(sp)
move.l a0,-(sp)
bsr.w StartTimer
movea.l (sp)+,a0
movem.w (sp)+,d0-d2
.not bra.w .cont
;******************************************************************
RemoveBomb
movem.l a0/d0-d2/d4,-(sp)
movea.l PFAdr,a0
moveq #-1,d7
move.w d2,d4
move.w PFWidth,d2
bsr.w AddAround ;IN: a0-PFAdr, d2-PFWidth, d4-offset, d7- value to add
clr.b (a0,d4.w)
move.w d4,-(sp)
move.w MaxRandRange,d0
bsr.w Rand
movea.l SeedFillStack,a0 ;contains offsets of free buttons
move.w (a0,d0.w*2),d4
move.w PFWidth,d2
movea.l PFAdr,a0
moveq #1,d7
bsr.w AddAround
move.b #mgg_Bomb/4,(a0,d4.w)
move.w (sp)+,d4
move.w #mgg_Bomb/4,d1
bsr.w GetAround ; "" ,OUT: d0-number of bombs around
move.b d0,(a0,d4.w)
movem.l (sp)+,a0/d0-d2/d4
rts
;******************************************************************
HandleMouseMove tst.b Play
beq.s .exit
tst.b Disable
bne.s .exit
tst.b Pause
bne.s .exit
move.w (im_MouseX,a0),d0
move.w (im_MouseY,a0),d1
sub.w MinPFX,d0 ;check range
bmi.w .out
sub.w MinPFY,d1
bmi.w .out
cmp.w PFXPix,d0
bhs.s .out
cmp.w PFYPix,d1
bhs.s .out
;in
TRAPRMB
bra.w CollectLoop
.out FREERMB
.exit bra.w CollectLoop
;******************************************************************
HandleGadgetDown ;double-clicking on the sun gadget means iconify
lea (.time,pc),a2
tst.b SunPressedOnce ;is this the first time?
bne.s .testdouble ;no
st SunPressedOnce
move.l (im_Seconds,a0),(a2) ;save time of this event
move.l (im_Micros,a0),4(a2)
bra.w CollectLoop
.testdouble clr.b SunPressedOnce
move.l (a2),d0 ;start seconds
move.l 4(a2),d1 ; micros
move.l (im_Seconds,a0),d2 ;current secs.
move.l (im_Micros,a0),d3 ;current micros
movea.l IntuiBase,a6
jsr (_LVODoubleClick,a6) ;double clicked?
tst.l d0
beq.w CollectLoop ;no
subq.l #8,a7 ;to be compatible with MenuPick
bsr.w mh_Iconify
addq.l #8,a7
bra.w CollectLoop
.time dc.l 0,0
;******************************************************************
HandleGadgetUP bsr.w InitBeforeStart
tst.l PFAdr
beq.w ExitSweeper
bra.w CollectLoop
;******************************************************************
ESC = 27
HandleVanillaKeys
move.w (im_Code,a0),d2
move.w (im_Qualifier,a0),d3
pea (.exit,pc) ;!!!!!!!!!!!!!!!!!!!!!!!!!
move.b d2,d0
bsr.w uppercaseD0
btst #IEQUALIFIERB_LCOMMAND,d3
bne.s .lramiga
btst #IEQUALIFIERB_RCOMMAND,d3
bne.s .lramiga
cmpi.b #'H',d0
beq.s mh_HiScores
cmpi.b #ESC,d2
beq.s vk_Exit
cmpi.b #'*',d0
beq.w vk_Iconify
cmpi.b #'P',d0 ;set/break pause
beq.s vk_Pause
cmpi.b #' ',d2 ;SPACE=START
beq.s .start
addq.l #4,sp ;(.exit,pc)
.exit bra.w CollectLoop
.start bsr.w InitBeforeStart
tst.l PFAdr
bne.s .ok
addq.l #4,sp
bra.w ExitSweeper
.ok rts
.lramiga
;test level change
cmpi.b #'1',d0
blo.s .no
cmpi.b #'5',d0
bhi.s .no
subi.b #'0',d0
bsr.w NewLevelNoMenu
rts
.no cmpi.b #'H',d0
beq.w mh_HiScores
cmpi.b #'Q',d0
beq.s vk_Exit
cmpi.b #'?',d0
beq.s vk_About
cmpi.b #'I',d0
beq.w vk_Iconify
cmpi.b #'A',d0
beq.w vk_AdjustPrefs
cmpi.b #'W',d0
beq.w mh_SavePrefs
cmpi.b #'S',d0
beq.s .start
cmpi.b #'P',d0
beq.s vk_Pause ;set/break pause
rts
vk_Iconify subq.l #4,sp ;to be compatible (see "Menu handlers")
bsr.w mh_Iconify
addq.l #4,sp
rts
vk_AdjustPrefs subq.l #4,sp ;to be compatible (see "Menu handlers")
bsr.w mh_AdjustPrefs
addq.l #4,sp
rts
vk_Exit addq.l #4,sp
bra.w ExitSweeper
vk_About bsr.w mh_About
rts
;-----------------------------------------------------
vk_Pause movea.l MyWindow,a0
movea.l IntuiBase,a6
jsr (_LVOZipWindow,a6)
rts
;------------------------------------
pause_Make FREERMB
bsr.w StopTimer
st Pause
move.b ([MyPrefs],mprf_Level),PausedLevel
;set titles
movea.l IntuiBase,a6
movea.l MyWindow,a0
move.w (wd_LeftEdge,a0),([MyPrefs],mprf_ZoomLeft) ;set prefs.
move.w (wd_TopEdge,a0),([MyPrefs],mprf_ZoomTop)
move.l #-1,a1
lea (.pausetitle,pc),a2
jsr (_LVOSetWindowTitles,a6)
rts
.pausetitle dc.b 'MineSweeper - Paused',0
cnop 0,4
pause_Cont clr.b Pause
;set titles
movea.l IntuiBase,a6
movea.l MyWindow,a0
lea MyWinTitle,a1
lea MyWinScrTitle,a2
jsr (_LVOSetWindowTitles,a6)
move.b ([MyPrefs],mprf_Level),d0
cmp.b PausedLevel,d0
beq.s .nochange
bra.w NewLevel ;rts
.nochange tst.b Disable
bne.s .exit
tst.b Play
bne.s .playing
bsr.w InitBeforeStart
tst.l PFAdr
bne.s .ok
addq.l #4,sp
bra.w ExitSweeper
.ok rts
.playing TRAPRMB
move.b #RW_ACTUAL,d0
bsr.w RedrawWindow
bsr.w StartTimer
.exit rts
;******************************************************************
PutAllToFront movea.l IntuiBase,a6
movea.l MyScreen,a0
jsr (_LVOScreenToFront,a6)
movea.l MyWindow,a2
movea.l a2,a0
jsr (_LVOWindowToFront,a6)
movea.l a2,a0
jsr (_LVOActivateWindow,a6)
rts
;******************************************************************
StartTimer tst.b Pause
bne.s .exit
movea.l TimDevBase,a6
lea OldSysTime,a0
jsr (_LVOGetSysTime,a6) ;set start point
st TimerGo
.exit rts
ClearTimer clr.l MyTime
clr.l EndTime
clr.l EndTime+4
movea.l MyPrefs,a0
tst.b (mprf_CountDown,a0)
beq.s .zero
move.b (mprf_Level,a0),d0
subq.b #1,d0
ext.w d0
move.w (mhs_BestTimes,a0,d0.w*4),d0
move.w d0,MyTime+2
.zero clr.l MyTime+4 ;no rts here!
;--------
StopTimer clr.b TimerGo
rts
HandleTimer tst.b TimerGo
beq.s .ht_exit
;get current sys time
movea.l TimDevBase,a6
lea SysTime,a0
jsr (_LVOGetSysTime,a6) ;a0 is unchanged
movem.l (a0),d4/d5 ;store
lea OldSysTime,a1
jsr (_LVOSubTime,a6) ;new-old => new
movem.l d4/d5,(a1) ;write to OldSysTime
movea.l a0,a1
movea.l a0,a3 ;store
lea MyTime,a0
tst.b ([MyPrefs],mprf_CountDown)
beq.s .up
jsr (_LVOSubTime,a6)
bra.s .skip
.up jsr (_LVOAddTime,a6) ;add diference to my timer
.skip
movea.l a3,a1
lea EndTime,a0
jsr (_LVOAddTime,a6)
bsr.w RedrawTime
cmpi.l #MAXTIME,EndTime ;do you play too long?
blt.s .no
clr.b Win
bsr.w EndPlaying
lea toolong_Text,a1
lea toolong_Button,a2
bsr.w InformationReq
.no
.ht_exit bra.w CollectLoop
;******************************************************************
RedrawTime move.w TimeX,d0
move.w TimeY,d1
move.w MyTime+TV_SECS+2,d2
lea (OldSec,pc),a0 ;time changed?
cmp.w (a0),d2
beq.s .exit
move.w d2,(a0)
bsr.s DrawNumber
.exit rts
OldSec dc.w 0
;******************************************************************
DrawNumber ;IN: d2.w- number
; d0.w-x d1.w-y
MINUS = 10
ext.l d0
ext.l d1
movem.l d0/d1,-(sp)
bsr.s Num2String04 ;IN:d2-num;OUT:a2-string
movea.l MyWindow,a3
movea.l (wd_RPort,a3),a3
;**draw bevelled box
movea.l GadtoolsBase,a6
movem.l (sp),d0/d1
movea.l a3,a0
move.l #NUMBBOXX,d2
move.l #NUMBBOXY,d3
lea dbb_TagList2,a1
jsr (_LVODrawBevelBoxA,a6)
;**draw number
movem.l (sp)+,d0/d1
movea.l IntuiBase,a6
movea.l a2,a0
addq.l #NUMX,d0
addq.l #NUMY,d1
moveq #4-1,d7 ;draw 4 digits
.digitloop move.b (a0)+,d6
subi.b #'0',d6 ;get offset
bpl.s .ok
move.b #MINUS,d6
.ok ext.w d6
mulu.w #NUMPLANESIZE*2,d6
addi.l #rawNumbers,d6
lea img_Number,a1
move.l d6,(ig_ImageData,a1) ;img
movem.l d0/d1/a0,-(sp)
movea.l a3,a0 ;rp
jsr (_LVODrawImage,a6)
movem.l (sp)+,d0/d1/a0
addi.w #NUMNEXT,d0
dbra d7,.digitloop
rts
;******************************************************************
;**convert number in d2 to a string
Num2String04 ;IN:d2.w - number;OUT:a2 - ptr to string
lea (numfstring04,pc),a2
bra.s ns_Go ;rts
Num2String4 lea (numfstring4,pc),a2
ns_Go movem.l d0/d1/a0/a1/a3/a6,-(sp)
lea (dstream,pc),a1 ;data stream
move.w d2,(a1)
movea.l a2,a0 ;format string
lea (numostring,pc),a3 ;output string
lea (hChar,pc),a2
movea.l (EB,PC),a6
jsr (_LVORawDoFmt,a6) ;returns ptr. to end of data stream
;(which I don't need..)
movem.l (sp)+,d0/d1/a0/a1/a3/a6
lea (numostring,pc),a2
rts
hChar move.b d0,(a3)+
rts
dstream dc.w 0
numfstring04 dc.b '%04.d',0
numfstring4 dc.b '%4.d',0
numostring dcb.b 6,0
cnop 0,4
Num2StringDec ;IN:d0-number.l
;OUT:a0-ptr to string
lea (fstringdec,pc),a0
bra.s nsdh_Go
Num2StringHex lea (fstringhex,pc),a0
nsdh_Go movem.l d1-d7/a1-a6,-(sp)
lea (.dstream,pc),a1 ;data stream
move.l d0,(a1)
lea (.numostring,pc),a3 ;output string
clr.l (a3) ;clear the string
clr.l 4(a3)
clr.l 8(a3)
lea (hChar,pc),a2
movea.l (EB,PC),a6
jsr (_LVORawDoFmt,a6)
movem.l (sp)+,d1-d7/a1-a6
lea (.numostring,pc),a0
rts
.dstream dc.l 0
.numostring dcb.b 4*3,0
fstringdec dc.b '%lu',0 ;long, unsigned decimal
fstringhex dc.b '0x%08.lx',0
cnop 0,4
;******************************************************************
HandleNewSize tst.b DisplayTooBig
beq.s .skip
lea toobig_Text,a1
lea toobig_Button,a2
bsr.w InformationReq
clr.b DisplayTooBig
.skip
;**Changed size or just moved?
movea.l MyWindow,a0 ;check unexpected sizing
move.w WinWidth,d0
cmp.w (wd_Width,a0),d0
bne.w hns_unexp
move.w WinHeight,d0
cmp.w (wd_Height,a0),d0
bne.w hns_unexp
tst.b Pause ;was the window shrinked?
beq.s setWinPos ;no
bsr.w pause_Cont
bra.w CollectLoop
setWinPos ;**set new position to MyPrefs
movea.l MyWindow,a1
;refresh values
move.w (wd_Width,a1),d0
move.w (wd_Height,a1),d1
move.w d0,WinWidth
move.w d1,WinHeight
moveq #0,d2
move.b (wd_BorderLeft,a1),d2
sub.w d2,d0
move.b (wd_BorderRight,a1),d2
sub.w d2,d0
move.b (wd_BorderTop,a1),d2
sub.w d2,d1
move.b (wd_BorderBottom,a1),d2
sub.w d2,d1
move.w d0,InnWidth
move.w d1,InnHeight
move.w (wd_LeftEdge,a1),d0
move.w (wd_TopEdge,a1),d1
movea.l MyPrefs,a0
tst.b (mprf_CenterWindow,a0)
beq.s .yes
move.w d0,(mprf_WinX,a0)
move.w d1,(mprf_WinY,a0)
.yes move.w d0,WinX
move.w d1,WinY
;**now redraw and accept new level
tst.b IDidTheChange ;Me or user? (new level or moved?)
bne.s .newlevel
;moved => set new center
move.w WinWidth,d0
asr.w #1,d0
add.w WinX,d0
move.w d0,CenterPointX
move.w WinHeight,d0
asr.w #1,d0
add.w WinY,d0
move.w d0,CenterPointY
bra.s .skip
.newlevel bsr.w InitBeforeStart
tst.l PFAdr
beq.w ExitSweeper
.skip clr.b IDidTheChange
bra.w CollectLoop
hns_unexp ;Size is not the same as requested by ChangeWindowBox
tst.b IDidTheChange ;just low memory (or something...)?
bne.s .ok
;**check if the window was zoomed
move.w ZoomWidth,d0
cmp.w (wd_Width,a0),d0
bne.s .unexp
move.w ZoomHeight,d0
cmp.w (wd_Height,a0),d0
bne.s .unexp
;yes, the window was just zoomed
bsr.w pause_Make
bra.w CollectLoop
.unexp lea changed_Text,a1 ;or some stranger...?
lea changed_Button,a2
bsr.w InformationReq
st Disable
bra.w setWinPos
.ok lea unexp_Text,a1
lea unexp_Button,a2
bsr.w InformationReq
move.b LastLevel,d0
bsr.w NewLevelNoMenu
clr.b IDidTheChange
bra.w CollectLoop
;************************************************************************
CheckShowXmas
;--get current year
bsr.s GetCurrDate
lea CurrDate,a0
move.w (year,a0),d0
cmp.w LastXmas,d0 ;new year?
shi TestXmas
rts
;************************************************************************
CheckXmas ;check for xmas
tst.b TestXmas
beq.s .no
bsr.s GetCurrDate
lea CurrDate,a0
cmpi.w #24,(mday,a0)
bne.s .no
cmpi.w #12,(month,a0)
bne.s .no
move.w (year,a0),LastXmas
lea xmas_Text,a1
lea xmas_Button,a2
bsr.w InformationReq
clr.b TestXmas ;don't show anymore
st ([MyPrefs],mhs_NewHiscore)
.no rts
;************************************************************************
GetCurrDate movea.l IntuiBase,a6
lea Ctime,a0 ;secs
lea (4,a0),a1 ;micros
jsr (_LVOCurrentTime,a6)
movea.l UtilityBase,a6
move.l (a0),d0 ;get curr. secs.
lea CurrDate,a0 ;structure to fill
jsr (_LVOAmiga2Date,a6) ;get current date
rts
;************************************************************************
InitBeforeStart tst.b Pause
bne.s .exit
FREERMB
bsr.w ClearTimer
move.w PFBombs,BCount
move.l #img_Sun,Gadget_Image
move.b #RW_START,d0
bsr.w RedrawWindow
move.w MyTime+2,StartTime ;save real start time
tst.b ([MyPrefs],mprf_CountDown)
beq.s .ok
addq.w #1,MyTime+2
.ok
st Ready
bsr.w InitPF
clr.b Play
clr.b Win
st FirstTime
;set num. of buttons to press to win
move.w PFSize,d0
sub.w PFBombs,d0
sub.w PFWidth,d0
sub.w PFWidth,d0
sub.w PFHeight,d0
sub.w PFHeight,d0
addq.w #4,d0
move.w d0,WinCount
bsr.w CheckXmas
.exit rts
;-------------------------------------------
EndPlaying bsr.w StopTimer
clr.b Play
clr.b Ready
FREERMB
;fix a silly bug with timer
tst.b ([MyPrefs],mprf_CountDown)
beq.s .nobug
move.w StartTime,d0
cmp.w MyTime+2,d0
bge.s .nobug
move.w d0,MyTime+2
.nobug tst.b Win
beq.s .00
move.l #img_SunWon,Gadget_Image
bra.s .11
.00 move.l #img_SunLoose,Gadget_Image
.11
move.b #RW_END,d0
bsr.w RedrawWindow
tst.b Win
beq.s .0
move.w EndTime+2,d2
bsr.s CheckForScore ;IN:d2.w-time
.0 rts
;************************************************************************
CheckForScore movea.l MyPrefs,a0
lea (mhs_BestTimes,a0),a1
lea (mhs_BestNames,a0),a2
move.b (mprf_Level,a0),d0
subq.b #1,d0
ext.w d0
pea (.ret,pc)
cmp.w (a1,d0.w*4),d2
blo.s .setscore1
cmp.w (2,a1,d0.w*4),d2
blo.s .setscore2
addq.l #4,sp
.ret
rts ;you were not good enough!
.setscore1
cmpi.b #LCUSTOM-1,d0
bne.s .cont0
move.w (mhs_CustomWidth1,a0),(mhs_CustomWidth2,a0)
move.w (mhs_CustomHeight1,a0),(mhs_CustomHeight2,a0)
move.w (mhs_CustomBombs1,a0),(mhs_CustomBombs2,a0)
move.w PFWidth,d3
subq.w #2,d3
move.w d3,(mhs_CustomWidth1,a0)
move.w PFHeight,d3
subq.w #2,d3
move.w d3,(mhs_CustomHeight1,a0)
move.w PFBombs,(mhs_CustomBombs1,a0)
.cont0 move.w (a1,d0.w*4),d1 ;shift scores
move.w d2,(a1,d0.w*4)
move.w d1,(2,a1,d0.w*4)
mulu.w #NAMELEN*2,d0 ;shift names
lea (a2,d0.w),a2 ;new1
lea (NAMELEN,a2),a0 ;old2
movea.l a2,a1
.cp0 move.b (a1)+,(a0)+
bne.s .cp0
bra.s .setname
.setscore2 cmpi.b #LCUSTOM-1,d0
bne.s .cont1
move.w PFWidth,d3
subq.w #2,d3
move.w d3,(mhs_CustomWidth2,a0)
move.w PFHeight,d3
subq.w #2,d3
move.w d3,(mhs_CustomHeight2,a0)
move.w PFBombs,(mhs_CustomBombs2,a0)
.cont1 move.w d2,(2,a1,d0.w*4)
mulu.w #NAMELEN*2,d0
lea (NAMELEN,a2,d0.w),a2
.setname movea.l a2,a5 ;store
;**get players name
movea.l _ReqToolsBase,a6
moveq #NAMELEN-1,d0 ;max. name len
lea NameBuffer,a1
lea (entertext_Title,pc),a2
suba.l a3,a3
lea GSReqTags,a0 ;tags
jsr (_LVOrtGetStringA,a6)
tst.l d0
bne.s .gotit
lea (AnonymousPlayer,pc),a0
bra.s .cp1
.gotit lea NameBuffer,a0
.cp1 move.b (a0)+,(a5)+
bne.s .cp1
st ([MyPrefs],mhs_NewHiscore)
clr.b ValidHSText
bsr.w mh_HiScores
rts
AnonymousPlayer dc.b 'anonym :( ',0
entertext_Title dc.b 'Hi-score',0
cnop 0,4
;************************************************************************
;*******Menu handlers****************************************************
;************************************************************************
; warning: (sp) contains LONG,LONG,LONG -> 12 bytes (see mh_quit)
; a2 contains MyMenuItem addr. , d2-im_Code
mh_Level movea.l IntuiBase,a6
movea.l MenuStruct,a0
move.l d2,d0
ext.l d0 ;to be sure
jsr (_LVOItemAddress,a6)
movea.l d0,a0
move.w (mi_Flags,a0),d0 ;get flags
andi.w #CHECKED,d0 ;zero or CHECKED
beq.s mhl_exit
lea LevelItems,a1
move.l a2,d0
sub.l a1,d0
divu.w #mmi_SIZEOF,d0
addq.b #1,d0 ;d0 contains level number
NewLevel ;IN:d0-mprf_Level
movea.l MyPrefs,a0
move.b (mprf_Level,a0),LastLevel
move.b d0,(mprf_Level,a0)
tst.b Pause
bne.s mhl_exit
clr.b Disable
clr.b HandleNext
bsr.w ResizeWindow
mhl_exit rts
NewLevelNoMenu ;IN:d0-mprf_Level
;changes checkmark in menu
move.b d0,d6 ;store
;clear old checkmark
movea.l MyPrefs,a2
lea LevelItems,a3
move.b (mprf_Level,a2),d0
subq.b #1,d0
ext.w d0
mulu.w #mmi_SIZEOF,d0
move.w (mmi_Code,a3,d0.w),d0
movea.l MenuStruct,a0
ext.l d0 ;to be sure
movea.l IntuiBase,a6
jsr (_LVOItemAddress,a6)
movea.l d0,a0
andi.w #~CHECKED,(mi_Flags,a0) ;clear checkmark
;set new checkmark
move.b d6,d0
subq.b #1,d0
ext.w d0
mulu.w #mmi_SIZEOF,d0
move.w (mmi_Code,a3,d0.w),d0
movea.l MenuStruct,a0
ext.l d0 ;to be sure
jsr (_LVOItemAddress,a6)
movea.l d0,a0
ori.w #CHECKED,(mi_Flags,a0) ;set checkmark
move.b d6,d0
bra.s NewLevel
;************************************************************************
mh_About lea about_Text,a1
lea about_Button,a2
lea AboutTags,a0
suba.l a3,a3
suba.l a4,a4
movea.l _ReqToolsBase,a6
jsr (_LVOrtEZRequestA,a6) ;I don't care about the results
rts
;************************************************************************
mh_Start bsr.w InitBeforeStart
tst.l PFAdr
beq.s mh_Quit
rts
;************************************************************************
mh_Pause bra.w vk_Pause ;rts
;************************************************************************
mh_Quit lea (12,sp),sp ;rts,a2,d2
bra.w ExitSweeper
;*****************************************************************
mh_HiScores tst.b ValidHSText
bne.s .show
bsr.w MakeHighScores
st ValidHSText
.show
movea.l MyPrefs,a0
tst.b (mhs_NewHiscore,a0)
beq.s .dontsave
tst.b (mhs_Valid,a0)
beq.s .dontsave
lea HiScoresButtonSave,a2
bsr.s .disphsc
tst.l d0
beq.s .skipsaving
bsr.w SaveHiScores
.skipsaving rts
.dontsave lea HiScoresButton,a2
.disphsc lea HiScoresText,a1
lea HiScoresTags,a0
suba.l a3,a3
suba.l a4,a4
movea.l _ReqToolsBase,a6
jsr (_LVOrtEZRequestA,a6)
rts
;*****************************************************************
mh_SaveScores bsr.w SaveHiScores
rts
;*****************************************************************
mh_ClearCustom
lea surec_Text,a1
lea surec_Button,a2
bsr.w InformationReq
tst.l d0
beq.s .exit
clr.b ValidHSText
movea.l MyPrefs,a0
st (mhs_NewHiscore,a0)
clr.b (mhs_CustomName1,a0)
clr.b (mhs_CustomName2,a0)
move.w #MAXTIME,(mhs_CustomTime1,a0)
move.w #MAXTIME,(mhs_CustomTime2,a0)
lea (mhs_CustomInfo,a0),a0
moveq #(mhs_CIEnd-mhs_CustomInfo)/2-1,d0
.clr clr.w (a0)+
dbra d0,.clr
bsr.s mh_HiScores
.exit rts
;*****************************************************************
mh_ClearAll lea surea_Text,a1
lea surea_Button,a2
bsr.w InformationReq
tst.l d0
beq.s .exit
clr.b ValidHSText
movea.l MyPrefs,a0
bsr.w ClearHighScores
bsr.w mh_HiScores
.exit rts
;*****************************************************************
mh_AdjustPrefs rts
;*****************************************************************
newToolTypes dc.l 0
nosavemem_Text dc.b 'Not enough memory',0
nosavemem_Button dc.b 'I see..',0
notsaved_Text dc.b 'Preferences couldn',39,'t be saved',0
notsaved_Button dc.b 'I see..',0
cnop 0,4
;-----------------------------------------
SEGMENTSIZE = TOOLTYPEITEMS*40
mh_SavePrefs
;alloc. mem for tool types array
move.l #SEGMENTSIZE,d7 ;d7-allocated size
mhsp_TryAgain ;to this label jumps EndOfSpace
move.l d7,d6
move.l d7,d0 ;d6-couter
move.l #MEMF_PUBLIC,d1
bsr.w ADDALLOC
lea (newToolTypes,pc),a0
move.l d0,(a0)
beq.w sp_nomem
movea.l (newToolTypes,pc),a2
lea ((TOOLTYPEITEMS+1)*4,a2),a3 ;skip pointers
subi.l #(TOOLTYPEITEMS+1)*4,d6
movea.l MyPrefs,a5
lea PrefItems,a0
.sp_loop tst.l (a0) ;end?
beq.s .done
movea.l (mpi_PItemName,a0),a4
movea.l (mpi_SaveHandler,a0),a1
move.l a3,(a2)+ ;save text pointer
;now create text of the tool type
move.l a0,-(sp)
jsr (a1) ;IN:a3-tt_text a4-prefitem text, a5-MyPrefs
movea.l (sp)+,a0
lea (mpi_SIZEOF,a0),a0
bra.s .sp_loop
.done
clr.l (a2) ;end of array of CHAR *
;*get tool types
movea.l (EB,PC),a6
lea (IconName,pc),a1
moveq #MinIconVer,d0
jsr (_LVOOpenLibrary,a6) ;"icon.library" V36
lea (IconBase,pc),a0
move.l d0,(a0)
beq.s .noiconlib
lea ProgramName,a0
movea.l (IconBase,pc),a6
jsr (_LVOGetDiskObjectNew,a6) ;get "mines.info" or something
lea (diskObj,pc),a0
move.l d0,(a0)
beq.s .closelib ;shouldn't happen...
movea.l d0,a1
movea.l (newToolTypes,pc),(do_ToolTypes,a1) ;set ToolTypes array
lea ProgramName,a0
jsr (_LVOPutDiskObject,a6) ;and save it to icon
tst.l d0
beq.s .errorsaving
.freeobj movea.l (diskObj,pc),a0
jsr (_LVOFreeDiskObject,a6)
.closelib move.l (EB,PC),a6
movea.l (IconBase,pc),a1
jsr (_LVOCloseLibrary,a6)
.freemem movea.l (newToolTypes,pc),a1
bsr.w FreeMemBlock
rts ;exit this section
;--------------------
.errorsaving lea (notsaved_Text,pc),a1
lea (notsaved_Button,pc),a2
bsr.w InformationReq
bra.s .freeobj
.noiconlib lea (noicon_Text,pc),a1 ;see LoadPreferences
lea (noicon_Button,pc),a2
bsr.w InformationReq
bra.s .freemem
sp_nomem lea (nosavemem_Text,pc),a1
lea (nosavemem_Button,pc),a2
bsr.w InformationReq
rts
;-------------------------------------------------------------
;this piece of code allocates new block of memory, when the old is too small
EndOfSpace
movea.l (newToolTypes,pc),a1
bsr.w FreeMemBlock ;free old buffer
;try to allocate more space
addi.l #SEGMENTSIZE,d7
lea (12,a7),a7 ;rts_tt_Write,rts_sp_Sub,movea.l (sp)+,a0
bra.w mhsp_TryAgain
;-------------------------------------------------------------
tt_Write ;Copies text from (a4) to (a3) without the zero byte.
;Checks if there is enough free memory for this operation.
;IN: a4-source text a3-destination buffer (d6-counter)
.cp subq.l #1,d6
bmi.w EndOfSpace
move.b (a4)+,(a3)+
bne.s .cp
subq.l #1,a3 ;delete the zero byte
addq.l #1,d6
rts
tt_WriteEqual ;writes "=" to (a3)
lea (eqchar,pc),a4
bra.s tt_Write ;don't use "bsr"
;tt_Write would be 3rd iteration (must be 2nd)!
eqchar dc.b '=',0
cnop 0,4
tt_WriteZero ;writes zero byte and subcrements d6(counter).
;Checking for memory was already done by tt_Write.
;Only call this routine once after some tt_Write(s).
clr.b (a3)+
subq.l #1,d6
rts
;-------------------------------------------------------------
;Save preferences handlers
;IN: a3-tt_text a4-prefitem text a5-MyPrefs
;OUT: d0 - 0=OK else ERROR
; changes also a3
;in case of error is all memory free (I mean newToolTypes)
TOBRACKETS MACRO ;closes switch to brackets (e.G. (WBLIKE) )
;IN:a4-switch text
movea.l a4,a0 ;store
lea (lbrack,pc),a4 ;left bracket
bsr.w tt_Write
movea.l a0,a4 ;restore
bsr.w tt_Write
lea (rbrack,pc),a4 ;right bracket
bsr.w tt_Write
ENDM
lbrack dc.b '(',0
rbrack dc.b ')',0
cnop 0,4
WRITESWITCH MACRO ;IN:mprf_(Switch)
tst.b (\1,a5) ;switch specified?
bne.s .yes
TOBRACKETS
bra.s .exit
.yes bsr.w tt_Write
.exit bra.w tt_WriteZero ;rts
ENDM
WRITESTRUCTVAL MACRO ;IN: e.G. MyScreen, sc_Width, w (word)
bsr.w tt_Write
bsr.w tt_WriteEqual
moveq #0,d0
move.\3 ([\1],\2),d0
bsr.w Num2StringDec
movea.l a0,a4
bsr.w tt_Write
bra.w tt_WriteZero
ENDM
sp_PubScreen bsr.w tt_Write
bsr.w tt_WriteEqual
move.l (mprf_PubNameAdr,a5),d0 ;any PubScreen name?
bne.s .nameok ;yes
lea (nopubname,pc),a4
bra.s .skp
.nameok movea.l d0,a4
.skp bsr.w tt_Write
bra.w tt_WriteZero ;rts
nopubname dc.b '<Name>',0
cnop 0,4
;--------------------------------------
sp_CustomScreen WRITESWITCH mprf_CustomScreen
;--------------------------------------
sp_NotCenter WRITESWITCH mprf_CenterWindow
;--------------------------------------
sp_NotActiv WRITESWITCH mprf_WActivate
;--------------------------------------
sp_NoQuest WRITESWITCH mprf_Question
;--------------------------------------
sp_DeadQ WRITESWITCH mprf_DeadQ
;--------------------------------------
sp_CountD WRITESWITCH mprf_CountDown
;--------------------------------------
sp_NoRMouse WRITESWITCH mprf_RMouseGame
;--------------------------------------
sp_WBLike WRITESWITCH mprf_WBLike
;--------------------------------------
sp_Warn WRITESWITCH mprf_Warn
;--------------------------------------
sp_Scale WRITESWITCH mprf_ScaleGfx
;--------------------------------------
sp_ModeID bsr.w tt_Write
bsr.w tt_WriteEqual
move.l (mprf_ModeID,a5),d0
bsr.w Num2StringHex ;IN:d0-number.l, OUT:a0-string
movea.l a0,a4
bsr.w tt_Write
bra.w tt_WriteZero
;--------------------------------------
sp_SizeX WRITESTRUCTVAL MyScreen,sc_Width,w
;--------------------------------------
sp_SizeY WRITESTRUCTVAL MyScreen,sc_Height,w
;--------------------------------------
sp_WinX WRITESTRUCTVAL MyPrefs,mprf_WinX,w
;--------------------------------------
sp_WinY WRITESTRUCTVAL MyPrefs,mprf_WinY,w
;--------------------------------------
sp_ZoomX WRITESTRUCTVAL MyPrefs,mprf_ZoomLeft,w
;--------------------------------------
sp_ZoomY WRITESTRUCTVAL MyPrefs,mprf_ZoomTop,w
;--------------------------------------
sp_Level bsr.w tt_Write
bsr.w tt_WriteEqual
move.b (mprf_Level,a5),d0
subq.b #1,d0
ext.w d0
movea.l (.levTable,pc,d0.w*4),a4 ;get level name
bsr.w tt_Write
bra.w tt_WriteZero
.levTable dc.l ttEASY,ttMEDIUM,ttHARD,ttPROFI,ttCUSTOM
;--------------------------------------
sp_Iconify bsr.w tt_Write
bsr.w tt_WriteEqual
move.b (mprf_Iconify,a5),d0
ext.w d0
movea.l (.icTable,pc,d0.w*4),a4
bsr.w tt_Write
bra.w tt_WriteZero
.icTable dc.l iconIcon,iconMenu
;--------------------------------------
sp_CusWid WRITESTRUCTVAL MyPrefs,mprf_CustomWidth,w
;--------------------------------------
sp_CusHei WRITESTRUCTVAL MyPrefs,mprf_CustomHeight,w
;--------------------------------------
sp_CusBom WRITESTRUCTVAL MyPrefs,mprf_CustomBombs,w
;--------------------------------------
sp_Font bsr.w tt_Write
bsr.w tt_WriteEqual
move.l (mprf_FontName,a5),d0
beq.s .default
movea.l d0,a4
bra.s .skp
.default lea (defaultText,pc),a4
.skp bsr.w tt_Write
bra.w tt_WriteZero
;--------------------------------------
sp_FontSize bsr.w tt_Write
bsr.w tt_WriteEqual
move.w (mprf_FontSize,a5),d0
bne.s .ok
;zero font size means DESIGNED font
lea (designedText,pc),a4
bra.s .skip
.ok ext.l d0
bsr.w Num2StringDec
movea.l a0,a4
.skip bsr.w tt_Write
bra.w tt_WriteZero
;--------------------------------------
sp_Palette bsr.w tt_Write
bsr.w tt_WriteEqual
move.b (mprf_PaletteType,a5),d0
beq.s .colortable
subq.b #1,d0
ext.w d0
movea.l (.paltypes,pc,d0.w*4),a4
bsr.w tt_Write
.exit bra.w tt_WriteZero
.colortable lea ScreenPalette+4,a1
move.b #PALENTRIES,d2
.ctloop moveq #0,d0
move.b (3,a1),d1 ;RED
bfins d1,d0{8:8}
move.b (7,a1),d1 ;GREEN
bfins d1,d0{16:8}
move.b (11,a1),d1 ;BLUE
bfins d1,d0{24:8}
bsr.w Num2StringHex
movea.l a0,a4
bsr.w tt_Write
lea (3*4,a1),a1
subq.b #1,d2
beq.s .exit
lea (.comma,pc),a4
bsr.w tt_Write
bra.s .ctloop
.paltypes dc.l ptStandard,ptMagicWB,ptWBLike
.comma dc.b ',',0
cnop 0,4
;--------------------------------------
sp_GfxType bsr.w tt_Write
bsr.w tt_WriteEqual
move.b (mprf_GfxType,a5),d0
ext.w d0
movea.l (.gtype,pc,d0.w*4),a4
bsr.w tt_Write
bra.w tt_WriteZero
.gtype dc.l gfxStandard,gfxMagicWB
;*****************************************************************
mh_JoinScores
clr.w LastXmas
;alloc JoinPrefsBuf
move.l #prf_SIZEOF,d0
moveq #0,d1
bsr.w ADDALLOC
move.l d0,JoinPrefsBuf
beq.w fatalerror
;alloc file requester
movea.l _ReqToolsBase,a6
move.l #RT_FILEREQ,d0
suba.l a0,a0 ;no tags
jsr (_LVOrtAllocRequestA,a6)
move.l d0,JoinRequester
beq.w norequester
;get files to join
movea.l d0,a1
lea JoinFilename,a2
lea JoinGetTitle,a3
lea JoinGetTags,a0
jsr (_LVOrtFileRequestA,a6)
move.l d0,JoinFileList
beq.w .nofilelist
;change dir
movea.l JoinRequester,a0
movea.l DosBase,a6
move.l (rtfi_Dir,a0),d1
move.l #ACCESS_READ,d2
jsr (_LVOLock,a6)
move.l d0,JoinDirLock ;store the lock
move.l d0,d1
jsr (_LVOCurrentDir,a6)
move.l d0,JoinOldDir
;------------------------------------------------------
movea.l JoinFileList,a3 ;filelist
lea (join_errors,pc),a0
clr.b (a0)
.ex
move.l (rtfl_Name,a3),d0
bsr.w LOAD_FILE ;IN:d0-filename ;OUT: d0-adr. or 0 ;d1- len
tst.l d0
beq.s .nosuchfile
lea (fb,pc),a0 ;store buffer
move.l d0,(a0)
bfclr d1{0:16}
bne.s .nohiscores ;too big to be hiscore file
subq.w #1,d1 ;file lenght
bmi.s .nohiscores ;empty file
movea.l d0,a5
movea.l JoinPrefsBuf,a4
bsr.w GetMHS ;extract the data
tst.l d0
bne.s .nohiscores
bsr.w Join2Scores
st ([MyPrefs],mhs_NewHiscore)
clr.b ValidHSText
;free file buffer
.freefile movea.l (fb,pc),a1
bsr.w FreeMemBlock
.next tst.l (a3) ;rtfl_Next
beq.s .done ;all examined?
movea.l (a3),a3 ;Next
bra.s .ex
.nosuchfile lea (join_errors,pc),a0
st (a0)
lea (examine_Text,pc),a0
bsr.w PrintText
move.l (rtfl_Name,a3),a0
bsr.w PrintText
lea (ERRNOFILE,pc),a0
bsr.w PrintText
bra.s .next
.nohiscores lea (join_errors,pc),a0
st (a0)
lea (examine_Text,pc),a0
bsr.w PrintText
move.l (rtfl_Name,a3),a0
bsr.w PrintText
lea (ERRNOSCORES,pc),a0
bsr.w PrintText
bra.s .freefile
;-------------------------------------------
.done movea.l _ReqToolsBase,a6
movea.l JoinFileList,a0
jsr (_LVOrtFreeFileList,a6)
movea.l DosBase,a6
move.l JoinDirLock,d1
jsr (_LVOUnLock,a6)
move.l JoinOldDir,d1
jsr (_LVOCurrentDir,a6)
.nofilelist movea.l _ReqToolsBase,a6
movea.l JoinRequester,a1
jsr (_LVOrtFreeRequest,a6)
movea.l JoinPrefsBuf,a1
bsr.w FreeMemBlock
tst.b (join_errors,pc)
beq.s .noerr
lea (joinerr_Text,pc),a1
lea (joinerr_Button,pc),a2
bsr.w InformationReq
.noerr bsr.w mh_HiScores
rts
norequester
fatalerror lea (jnm_Text,pc),a1
lea (jnm_Button,pc),a2
bsr.w InformationReq
rts
ERRNOFILE dc.b 9,' ** no such file.',10,0
ERRNOSCORES dc.b 9,' ** not a Hi-Score file.',10,0
examine_Text dc.b 'File: ',0
jnm_Text dc.b 'Not enough memory.',0
jnm_Button dc.b 'Continue',0
joinerr_Text dc.b 'Some errors occured.',10
dc.b 'See MineSweeper output window.',0
joinerr_Button dc.b 'OK',0
join_errors dc.b 0 ;BOOL
cnop 0,4
;----------------------------------------------------------------
COMPARE MACRO
move.w (mhs_\1Time1,a0),d0 ;loaded time
lea (mhs_\1Name1,a0),a2
bsr.s .check\@
move.w (mhs_\1Time2,a0),d0
lea (mhs_\1Name2,a0),a2
pea (.exit\@,pc)
.check\@ cmp.w (mhs_\1Time1,a1),d0 ;destination hiscores
bhs.s .try2nd\@
;insert d0,a2 to first place
movem.l d0/a2,-(sp)
move.w (mhs_\1Time1,a1),d0
lea (mhs_\1Name1,a1),a2
bsr.s .set2nd\@
movem.l (sp)+,d0/a2
move.w d0,(mhs_\1Time1,a1)
lea (mhs_\1Name1,a1),a3
bra.s .cpname\@
.try2nd\@ cmp.w (mhs_\1Time2,a1),d0
bhs.s .trynext\@
;set d0,a2 to second place
.set2nd\@ move.w d0,(mhs_\1Time2,a1)
lea (mhs_\1Name2,a1),a3
.cpname\@ moveq #NAMELEN-1,d0
.cp\@ move.b (a2)+,(a3)+ ;set new name
dbra d0,.cp\@
.trynext\@ rts
.exit\@
ENDM
Join2Scores movem.l a0-a3,-(sp)
movea.l JoinPrefsBuf,a0
movea.l MyPrefs,a1
COMPARE Easy
COMPARE Normal
COMPARE Hard
COMPARE Profi
;now handle custom levels
;check 1st sour match 1st dest
; yes
; better 1st sour 1st dest
; yes
; copy 1st dest to 2nd dest
; copy 1st sour to 1st dest
; exit
; no
; no
; check2nd
; check 1st sour match 2nd dest
; yes
; better 1st sour 2nd dest
; yes
; copy 1st sour to 2nd dest
; exit
; no
; no
; repeat all for 2nd sour
; exit
;--------------------------------------------------
CHECKBETTER MACRO ;IN: sour pos., dest pos.
;OUT: Zero<=>True else false
;check \1 sour match \2 dest
move.w (mhs_CustomWidth\2,a1),d0
beq.s .matched\@ ;no custom defined yet
cmp.w (mhs_CustomWidth\1,a0),d0
bne.s .nomatchcb\@
move.w (mhs_CustomHeight\1,a0),d0
cmp.w (mhs_CustomHeight\2,a1),d0
bne.s .nomatchcb\@
move.w (mhs_CustomBombs\1,a0),d0
cmp.w (mhs_CustomBombs\2,a1),d0
bne.s .nomatchcb\@
.matched\@
; better \1 sour than \2 dest?
move.w (mhs_CustomTime\1,a0),d0
cmp.w (mhs_CustomTime\2,a1),d0
bhs.s .nomatchcb\@
moveq #0,d0
bra.s .exit\@
.nomatchcb\@ moveq #-1,d0
.exit\@
ENDM
;--------------------------------------------------
COPY MACRO ;IN: 1|2, sour data , 1|2, dest data
move.w mhs_CustomTime\1(\2),mhs_CustomTime\3(\4)
move.w mhs_CustomWidth\1(\2),mhs_CustomWidth\3(\4)
move.w mhs_CustomHeight\1(\2),mhs_CustomHeight\3(\4)
move.w mhs_CustomBombs\1(\2),mhs_CustomBombs\3(\4)
movea.l \2,a2 ;store regs
movea.l \4,a3
;copy the name
lea (mhs_CustomName\1,a2),a2
lea (mhs_CustomName\3,a3),a3
.cp\@ move.b (a2)+,(a3)+
bne.s .cp\@
ENDM
;--------------------------------------------------
DOCUSTOM MACRO ;IN: 1|2 for 1st|2nd
CHECKBETTER \1,1
bne.s .check2nd\@
;matched
COPY \1,a1,2,a1 ;works also with 2nd to 2nd
COPY \1,a0,\1,a1 ; - "" -
bra.w .exitcust
.check2nd\@ CHECKBETTER \1,2
bne.s .nomatch\@
COPY \1,a0,2,a1
bra.w .exitcust
.nomatch\@
ENDM
;--------------------------------------------------
DOCUSTOM 1
DOCUSTOM 2 ;bra.s .exitcust
moveq #0,d0 ;just bytes
.exitcust
movem.l (sp)+,a0-a3
rts
;*****************************************************************
noWBLib_text dc.b '"workbench.library" V36+ required to iconify.',0
noWBLib_button dc.b 'I see..',0
cantic_Text dc.b 'Couldn',39,'t iconify.',0
cantic_Button dc.b 'Continue',0
WBLibName dc.b 'workbench.library',0
errunic_Text dc.b 'Couldn',39,'t uniconify correctly.',10
dc.b 'Some memory may be wasted.',0
errunic_Button dc.b 'I see.',0
MinesMenuName
MinesPortName dc.b 'MineSweeper',0
cnop 0,4
WBLibBase dc.l 0
MinesMsgPort dc.l 0
MinesAppMenuItem dc.l 0
mh_Iconify
;open "workbench.library"
movea.l (EB,PC),a6
lea (WBLibName,pc),a1
moveq #MinWBVer,d0
jsr (_LVOOpenLibrary,a6)
lea (WBLibBase,pc),a0
move.l d0,(a0)
bne.s .ok
lea (noWBLib_text,pc),a1
lea (noWBLib_button,pc),a2
bsr.w InformationReq
rts
.ok
bsr.w StopTimer
;set actual window size and position to tag list
;close the window
bsr.w ClearMenu
bsr.w CloseMyWindow
clr.l OldIDCMP
;close the screen
bsr.w FreeGfx
bsr.w FreeVisualInfo
bsr.w CloseMyScreen ;also frees draw info
pea (.ret,pc)
movea.l MyPrefs,a0
cmpi.b #ICON_ICON,(mprf_Iconify,a0)
beq.w ic_AppIcon
bra.w ic_AppMenu
.ret tst.l d0
bne.s .iccont
lea (cantic_Text,pc),a1
lea (cantic_Button,pc),a2
bsr.w InformationReq
bra.s .skipwaitport
;-----------------------------------
;Now wait for a message either from another MineSweeper (that's why it
;must be a public port)
;or from AppMenu
;-----------------------------------
.iccont
movea.l (EB,PC),a6
movea.l (MinesMsgPort,pc),a3 ;msgport
.waitloop movea.l a3,a0
jsr (_LVOWaitPort,a6)
.collectall movea.l a3,a0
jsr (_LVOGetMsg,a6)
tst.l d0
beq.s .waitloop ;no more messages
movea.l d0,a1
move.l (am_ID,a1),d6
.notmine jsr (_LVOReplyMsg,a6)
cmpi.l #'MINE',d6 ;message from another MineSweeper,
;or from appmenu-window-icon?
bne.s .collectall ;unknown
movea.l Semaphore,a0
jsr (_LVOObtainSemaphore,a6)
;collect rest of possible messages
.getall movea.l a3,a0
jsr (_LVOGetMsg,a6)
tst.l d0
bne.s .getall
pea (.ret2,pc)
movea.l MyPrefs,a0
cmpi.b #ICON_ICON,(mprf_Iconify,a0)
beq.w ic_RemAppIcon
bra.w ic_RemAppMenu
.ret2
tst.l d0 ;ret. code from ic_RemApp....
bne.s .ok1 ;currently always TRUE (V39)
lea (errunic_Text,pc),a1
lea (errunic_Button,pc),a2
bsr.w InformationReq
.ok1 movea.l (EB,PC),a6
movea.l Semaphore,a0
jsr (_LVOReleaseSemaphore,a6)
.skipwaitport
ic_ret movea.l (EB,PC),a6
movea.l (WBLibBase,pc),a1
jsr (_LVOCloseLibrary,a6)
st FromIconify
lea (12,sp),sp ;rts,a2,d2
clr.b Pause
bra.w iconify_Return
;----------------------------------------------------------
ic_AppIcon ;*get icon
movea.l (EB,PC),a6
lea (IconName,pc),a1
moveq #MinIconVer,d0
jsr (_LVOOpenLibrary,a6) ;"icon.library" V36
lea (IconBase,pc),a0
move.l d0,(a0)
beq.s .noiconlib
lea ProgramName,a0
movea.l (IconBase,pc),a6
jsr (_LVOGetDiskObjectNew,a6) ;get "mines.info" or something
lea (diskObj,pc),a0
move.l d0,(a0)
beq.s .closelib ;shouldn't happen...
movea.l (WBLibBase,pc),a6
move.l #'MINE',d0 ;id
moveq #0,d1 ;userdata
lea (ic_Name,pc),a0
movea.l (MinesMsgPort,pc),a1 ;msgport
suba.l a2,a2 ;lock
movea.l (diskObj,pc),a3 ;object
suba.l a4,a4 ;taglist
jsr (_LVOAddAppIconA,a6)
lea (AppIconPtr,pc),a0
move.l d0,(a0)
move.l d0,d2 ;store ret. code (0=fail)
movea.l (IconBase,pc),a6
movea.l (diskObj,pc),a0
jsr (_LVOFreeDiskObject,a6)
move.l d2,d0
.closelib move.l d0,-(sp) ;store return code
movea.l (EB,PC),a6
movea.l (IconBase,pc),a1
jsr (_LVOCloseLibrary,a6)
move.l (sp)+,d0
rts
.noiconlib moveq #0,d0
rts
AppIconPtr dc.l 0
ic_Name dc.b 'MineSweeper',0
cnop 0,4
;-----------------------------------------------
ic_RemAppIcon movea.l (WBLibBase,pc),a6
movea.l (AppIconPtr,pc),a0
jsr (_LVORemoveAppIcon,a6)
rts
;----------------------------------------------------------
ic_AppMenu ;OUT: d0 - 0=fail
;Add MineSweeper to AppMenu******
movea.l (WBLibBase,pc),a6
move.l #'MINE',d0 ;id
moveq #0,d1 ;userdata
lea (MinesMenuName,pc),a0 ;menu text
movea.l (MinesMsgPort,pc),a1 ;msgport
suba.l a2,a2 ;taglist
jsr (_LVOAddAppMenuItemA,a6)
lea (MinesAppMenuItem,pc),a0
move.l d0,(a0)
rts
;-----------------------------------------------
ic_RemAppMenu ;now remove me from AppMenu
movea.l (WBLibBase,pc),a6
movea.l (MinesAppMenuItem,pc),a0
jsr (_LVORemoveAppMenuItem,a6) ;as far as I know,
rts ;the result is always TRUE
;*****************************************************************
OpenPublicPort
;create msg port
movea.l (EB,PC),a6
jsr (_LVOCreateMsgPort,a6)
lea (MinesMsgPort,pc),a0
move.l d0,(a0)
beq.s .ret
movea.l d0,a1
move.b #1,(LN_PRI,a1) ;priority=1
lea (MinesPortName,pc),a0
move.l a0,(LN_NAME,a1)
jsr (_LVOAddPort,a6) ;make it public (IN: a1-port OUT: NIL)
.ret rts
ClosePublicPort
;remove port from public list
movea.l (EB,PC),a6
movea.l (MinesMsgPort,pc),a3 ;msgport
movea.l a3,a1
jsr (_LVORemPort,a6) ;IN: a1-port OUT:NIL
movea.l a3,a0
jsr (_LVODeleteMsgPort,a6) ;IN:a0-port OUT:NIL
rts
;*****************************************************************
;**Open libraries and/or display errors.
OpenReqTools movea.l (EB,PC),a6 ;This must be called at first!
moveq #MinReqToolsVer,d0
lea ReqToolsName,a1 ;"reqtools.library"
jsr (_LVOOpenLibrary,a6)
move.l d0,_ReqToolsBase
bne.s .exit
bsr.s OpenDos
beq.s .exit ;no dos.library (!?)
lea noreq_Text,a0
bsr.w PrintText
moveq #0,d0 ;set zero flag
.exit rts
OpenIntuition movea.l (EB,PC),a6 ;open "intuition.library"
moveq #MinIntuiVer,d0
lea IntuiName,a1
jsr (_LVOOpenLibrary,a6)
move.l d0,IntuiBase
bne.s .exit
lea nointui_Text,a1
lea nointui_Button,a2
bsr.w InformationReq
moveq #0,d0
.exit rts
OpenGraphics movea.l (EB,PC),a6 ;open "graphics.library"
moveq #MinGfxVer,d0
lea GfxName,a1
jsr (_LVOOpenLibrary,a6)
move.l d0,_GfxBase
bne.s .exit
lea nogfx_Text,a1
lea nogfx_Button,a2
bsr.w InformationReq
moveq #0,d0
.exit rts
OpenDos movea.l (EB,PC),a6 ;"dos.library"
moveq #MinDosVer,d0
lea DosName,a1
jsr (_LVOOpenLibrary,a6)
move.l d0,DosBase
bne.s .exit
lea nodos_Text,a1
lea nodos_Button,a2
bsr.w InformationReq
moveq #0,d0
.exit rts
OpenGadtools movea.l (EB,PC),a6 ;"gadtools.library"
moveq #MinGadToolsVer,d0
lea GadtoolsName,a1
jsr (_LVOOpenLibrary,a6)
move.l d0,GadtoolsBase
bne.s .exit
lea nogad_Text,a1
lea nogad_Button,a2
bsr.w InformationReq
moveq #0,d0
.exit rts
OpenUtility movea.l (EB,PC),a6 ;open "utility.library"
moveq #MinUtilityVer,d0
lea UtilityName,a1
jsr (_LVOOpenLibrary,a6)
move.l d0,UtilityBase
bne.s .exit
lea noutility_Text,a1
lea noutility_Button,a2
bsr.w InformationReq
moveq #0,d0
.exit rts
;**********************************************************
GetStartDirs clr.l OldDirectory
movea.l DosBase,a6
move.l WBmessage,d0 ;from WB?
beq.s .cli
;WB version
movea.l d0,a0
movea.l (sm_ArgList,a0),a0
movea.l (wa_Name,a0),a1
lea ProgramName,a2
.cp move.b (a1)+,(a2)+
bne.s .cp
move.l (wa_Lock,a0),d1
move.l d1,ProgDir
.cd jsr (_LVOCurrentDir,a6)
move.l d0,OldDirectory
rts
;*cli version
.cli move.l #ProgramName,d1
move.l #PROGNAMELEN,d2
jsr (_LVOGetProgramName,a6)
tst.l d0
beq.s .setmyname
.getdir jsr (_LVOGetProgramDir,a6)
move.l d0,ProgDir
rts
.setmyname lea (defaultName,pc),a0
lea ProgramName,a1
.cp1 move.b (a0)+,(a1)+
bne.s .cp1
bra.s .getdir
defaultName dc.b 'Mines',0
cnop 0,4
;------------------------------------------------------
FreeStartDir move.l OldDirectory,d1
beq.s .exit
movea.l DosBase,a6
jsr (_LVOCurrentDir,a6)
.exit rts
;**********************************************************
GetOutput ;IN:DosBase
;out: d0=output
movem.l d1/d2/a0/a1/a6,-(sp)
lea (myOutput,pc),a6
move.l a6,d1
move.l #MODE_NEWFILE,d2
movea.l DosBase,a6
jsr (_LVOOpen,a6)
lea (MyOut,pc),a0
move.l d0,(a0)
movem.l (sp)+,d1/d2/a0/a1/a6
rts
myOutput dc.b 'CON://600/150/MineSweeper output window/CLOSE/AUTO/SIMPLE/INACTIVE/WAIT',0
cnop 0,4
MyOut dc.l 0
;**********************************************************
PrintText ;IN: a0-null terminated string
movem.l d0-d3/a0/a1/a6,-(sp)
movea.l DosBase,a6
move.l (MyOut,pc),d1 ;identif. vystupu
bne.s .ok
bsr.s GetOutput
move.l d0,d1
beq.s .exit
.ok moveq #0,d3 ;lenght
move.l a0,d2
.1 tst.b (a0)+
beq.s .endtext
addq.l #1,d3
bra.s .1
.endtext jsr (_LVOWrite,a6) ;I don't care about the result
.exit movem.l (sp)+,d0-d3/a0/a1/a6
rts
;*****************************************************************
InitPF ;Two fields are allocated:
;1. numbers, bombs, empty gadgets, noflags
;2. 0 - empty gadget
; 1 - pressed gadgets
; 2 - flag
move.l PFAdr,d1
beq.s .nopf
move.w PFWidth,d0
mulu.w PFHeight,d0
cmp.w PFSize,d0
beq.s .allocated
;first free last PF
movea.l d1,a1
bsr.w FreeMemBlock
.nopf
;alloc new
move.w PFWidth,d0
mulu.w PFHeight,d0
move.l d0,d1 ;check the size (max 65535)
andi.l #$ffff0000,d1
bne.w .ipf_toobig
move.w d0,PFSize
ext.l d0
move.l d0,d2 ;store
add.l d0,d0 ;allocate 2 fields
moveq #0,d1
bsr.w ADDALLOC
move.l d0,PFAdr
beq.w .ipf_error
;alloc buffer for seedfill
move.l SeedFillStack,d0
beq.s .noyet
movea.l d0,a1
bsr.w FreeMemBlock
.noyet move.w PFWidth,d0
mulu.w PFHeight,d0
mulu.w #12,d0 ;12 bytes per button
addi.l #24,d0 ;to be sure
move.l d0,d6 ;store
moveq #0,d1
bsr.w ADDALLOC
move.l d0,SeedFillStack
beq.w .ipf_error
add.l d6,d0 ;end of the area
move.l d0,SeedFillSP ;ptr to the stack
;**fill it with values
.allocated ;first clear both fields
movea.l PFAdr,a0
move.w PFSize,d0
add.w d0,d0 ;both
subq.w #1,d0
.clr clr.b (a0)+
dbra d0,.clr
;**bombs
movea.l IntuiBase,a0
move.l (ib_Micros,a0),RndSeed
;use SeedFillStack to generate random values
movea.l SeedFillStack,a0
move.w PFWidth,d3
move.w PFHeight,d4
subq.w #1,d3
subq.w #1,d4
moveq #1,d1 ;start for y
.yloop moveq #1,d0 ;start for x
.xloop move.w d1,d2 ;position in the PF
mulu.w PFWidth,d2
add.w d0,d2
move.w d2,(a0)+
addq.w #1,d0 ;next x
cmp.w d3,d0 ;PFWidth-1
bne.s .xloop
addq.w #1,d1 ;next y
cmp.w d4,d1 ;PFHeight-1
bne.s .yloop
movea.l PFAdr,a0
movea.l SeedFillStack,a1
move.w PFBombs,d7
subq.w #1,d7
move.w PFWidth,d0
move.w PFHeight,d3
subq.w #2,d0
subq.w #2,d3
mulu.w d0,d3 ;range for Rand
subq.w #1,d3
.next
move.w d3,d0 ;range
addq.w #1,d0
bsr.w Rand
move.w (a1,d0.w*2),d1 ;get PF pos. of the bomb
move.w (a1,d3.w*2),(a1,d0.w*2) ;and move last item to current
move.b #mgg_Bomb/4,(a0,d1.w)
subq.w #1,d3 ;decrease range
dbra d7,.next
addq.w #1,d3
move.w d3,MaxRandRange
;**numbers
movea.l PFAdr,a0
moveq #1,d1 ;ypos
move.w PFWidth,d2 ;maxx
move.w PFHeight,d3 ;maxy
.looplines moveq #1,d0 ;xpos
.loopcolumns move.w d1,d4
mulu.w d2,d4
add.w d0,d4
cmpi.b #mgg_Bomb/4,(a0,d4.w)
bne.s .no
moveq #1,d7
bsr.w AddAround
.no addq.w #1,d0 ;next column
cmp.w d2,d0
bne.s .loopcolumns
addq.w #1,d1 ;next line
cmp.w d3,d1
bne.w .looplines
;fill the border to range an area for seedfill
movea.l PFAdr,a0
adda.w PFSize,a0
movea.l a0,a1
move.w PFWidth,d0
move.w d0,d1
mulu.w PFHeight,d1
adda.w d1,a1
suba.w d0,a1
subq.w #1,d0
.fb1 move.b #1,(a0)+
move.b #1,(a1)+
dbra d0,.fb1
movea.l PFAdr,a0
adda.w PFSize,a0
move.b #1,(a0) ;first line, first col.
move.w PFWidth,d0
subq.w #1,d0
adda.w d0,a0
addq.w #1,d0
move.w PFHeight,d1
subq.w #2,d1
.fb2 move.b #1,(a0) ;prev. line, last col.
move.b #1,(1,a0) ;next line, first col.
adda.w d0,a0
dbra d1,.fb2
move.b #1,(a0) ;last line, last col.
rts
.ipf_error lea nopf_Text,a1
lea nopf_Button,a2
bsr.w InformationReq
rts
.ipf_toobig lea pfbig_Text,a1
lea pfbig_Button,a2
bsr.w InformationReq
clr.l PFAdr
rts
;*****************************************************************
;increase all free items next to this
AddAround ;IN: a0-PFAdr, d2-PFWidth, d4-offset, d7- value to add
move.w d4,-(sp)
cmpi.b #mgg_Bomb/4,(-1,a0,d4.w)
beq.s .0
add.b d7,(-1,a0,d4.w) ;l
.0 cmpi.b #mgg_Bomb/4,(1,a0,d4.w)
beq.s .1
add.b d7,(1,a0,d4.w) ;r
.1 sub.w d2,d4
cmpi.b #mgg_Bomb/4,(a0,d4.w)
beq.s .2
add.b d7,(a0,d4.w) ;u
.2 cmpi.b #mgg_Bomb/4,(-1,a0,d4.w)
beq.s .3
add.b d7,(-1,a0,d4.w) ;ul
.3 cmpi.b #mgg_Bomb/4,(1,a0,d4.w)
beq.s .4
add.b d7,(1,a0,d4.w) ;ur
.4 add.w d2,d4
add.w d2,d4
cmpi.b #mgg_Bomb/4,(a0,d4.w)
beq.s .5
add.b d7,(a0,d4.w) ;d
.5 cmpi.b #mgg_Bomb/4,(-1,a0,d4.w)
beq.s .6
add.b d7,(-1,a0,d4.w) ;dl
.6 cmpi.b #mgg_Bomb/4,(1,a0,d4.w)
beq.s .7
add.b d7,(1,a0,d4.w) ;dr
.7 move.w (sp)+,d4
rts
;*****************************************************************
;get num. of items around
GetAround ;IN: a0-PFAdr, d1-num. to check, d2-PFWidth, d4-offset
;OUT: d0-num.
move.w d4,-(sp)
clr.b d0
cmp.b (-1,a0,d4.w),d1
bne.s .0
addq.b #1,d0 ;l
.0 cmp.b (1,a0,d4.w),d1
bne.s .1
addq.b #1,d0 ;r
.1 sub.w d2,d4
cmp.b (a0,d4.w),d1
bne.s .2
addq.b #1,d0 ;u
.2 cmp.b (-1,a0,d4.w),d1
bne.s .3
addq.b #1,d0 ;ul
.3 cmp.b (1,a0,d4.w),d1
bne.s .4
addq.b #1,d0 ;ur
.4 add.w d2,d4
add.w d2,d4
cmp.b (a0,d4.w),d1
bne.s .5
addq.b #1,d0 ;d
.5 cmp.b (-1,a0,d4.w),d1
bne.s .6
addq.b #1,d0 ;dl
.6 cmp.b (1,a0,d4.w),d1
bne.s .7
addq.b #1,d0 ;dr
.7 move.w (sp)+,d4
rts
;*****************************************************************
;IN: d0.w = range
Rand movem.l d4/d5,-(sp)
move.w d0,d5
beq.s .exit
move.w d5,d4
subq.w #1,d4
move.l RndSeed,d0
.loop add.l d0,d0
bhi.s .2
eor.l #$1d872b41,d0
.2 lsr.w #1,d4
bne.s .loop
move.l d0,RndSeed
tst.w d5
bne.s .3
swap d0
bra.s .4
.3 mulu d5,d0
.4 clr.w d0
swap d0
.exit movem.l (sp)+,d4/d5
rts
;*****************************************************************
GetButtonSizes
;get rast. font size first
move.l WinFont,d0
bne.s .setsize
moveq #12,d0
moveq #12,d1
bra.s .skip
.setsize movea.l d0,a0
move.w (tf_XSize,a0),d0
move.w (tf_YSize,a0),d1
addq.w #4,d0
addq.w #4,d1
.skip
cmpi.w #BUTMINX+4,d0
bge.s .ok1
move.w #BUTMINX+4,d0
.ok1 cmpi.w #BUTMINY+2,d1
bge.s .ok2
move.w #BUTMINY+2,d1
.ok2
;**get resolution and make buttons square
movea.l MyDrawInfo,a0
move.w (dri_ResolutionX,a0),d2
move.w (dri_ResolutionY,a0),d3
muls.w d2,d0
muls.w d3,d1
cmp.l d0,d1
blt.s .d1less
move.l d1,d0
.d1less move.l d0,d1
divs.w d2,d0
divs.w d3,d1
move.w d0,ButtWidth
move.w d1,ButtHeight
rts
;**************************************************************************
GetVisualInfo movea.l GadtoolsBase,a6
movea.l MyScreen,a0
suba.l a1,a1 ;no tags
jsr (_LVOGetVisualInfoA,a6)
move.l d0,VisualInfo ;check this result!
move.l d0,dbb_TagList1+4
move.l d0,dbb_TagList2+4
rts
FreeVisualInfo movea.l GadtoolsBase,a6
movea.l VisualInfo,a0 ;may be NULL
jsr (_LVOFreeVisualInfo,a6)
rts
;**************************************************************************
WritePlanes ;IN:a0- ptr to bm_Planes, a1-rawgfx ptr.
moveq #3,d0
.write move.l a1,(a0)+
lea (BUTNEXTPLANE,a1),a1
dbra d0,.write
rts
;----------------------------------------------
SETGFX MACRO
lea bm_Planes+bmap\1,a0
lea raw\1,a1
bsr.w WritePlanes
ENDM
SETMGFX MACRO
lea bm_Planes+bmap\1,a0
lea rawMagic\1,a1
bsr.w WritePlanes
ENDM
;----------------------------------------------
CreateGfx ;create button-bitmaps
;first set type of gfx (Standard/MagicWB)
tst.b ([MyPrefs],mprf_GfxType)
beq.s .standard
SETMGFX Flag
SETMGFX NoFlag
SETMGFX Bomb
SETMGFX Blowed
;set planepick/onoff for numbers
move.b #%11,img_Number+ig_PlanePick
bra.s .skipset
.standard SETGFX Flag
SETGFX NoFlag
SETGFX Bomb
SETGFX Blowed
.skipset
;**allocate MGG struct. and a RastPort structure
move.l #mgg_SIZEOF+rp_SIZEOF,d0
moveq #0,d1
bsr.w ADDALLOC
move.l d0,MGGfx
beq.w creategfx_error
;**allocate bitmaps
movea.l MGGfx,a3
movea.l MyScreen,a2
movea.l (sc_RastPort+rp_BitMap,a2),a2 ;friend bitmap
movea.l _GfxBase,a6
moveq #GADBPLNUM-1,d7
.loop move.w ButtWidth,d0
ext.l d0
move.w ButtHeight,d1
ext.l d1
moveq #BUTMAXBPL,d2
moveq #BMF_CLEAR,d3
movea.l a2,a0 ;friend bitmap
jsr (_LVOAllocBitMap,a6) ;V39
move.l d0,(a3)+
dbeq d7,.loop
beq.w creategfx_error
movea.l MGGfx,a2
lea (mgg_SIZEOF,a2),a3 ;my rast port
movea.l _GfxBase,a6
movea.l a3,a1
jsr (_LVOInitRastPort,a6) ;initialize my rastport
move.l WinFont,d0
beq.s .nofont
movea.l a3,a1 ;rp
movea.l d0,a0 ;TextFont
jsr (_LVOSetFont,a6)
.nofont
;**now comes the main part
;*I'll set each bitmap to MyRP and draw the gfx to it
;a3:my rp
;1. draw bevelled boxes (empty gadget etc.)
movea.l MGGfx,a5
movea.l a3,a0 ;rp
moveq #0,d0 ;x
move.l d0,d1 ;y
move.w ButtWidth,d2
ext.l d2
move.w ButtHeight,d3
ext.l d3
lea dbb_TagList1,a1
movea.l GadtoolsBase,a6
movem.l d0/d1/a0/a1,-(sp) ;(-)
move.w #mgg_NumOfNormal-1,d7
moveq #0,d6
.loopn movem.l (sp),d0/d1/a0/a1 ;restore damaged regs.
move.l (mgg_Empty,a5,d6.w),(rp_BitMap,a3) ;set bitmap
jsr (_LVODrawBevelBoxA,a6) ;draw to my bitmap
addq.w #4,d6 ;next bmap
dbra d7,.loopn
movem.l (sp)+,d0/d1/a0/a1 ;(+)
;2. recessed bevelled boxes
movea.l MGGfx,a5
move.l (mgg_EmptyRecessed,a5),(rp_BitMap,a3) ;set bitmap
movea.l a3,a0 ;rp
moveq #0,d0 ;x
move.l d0,d1 ;y
move.w ButtWidth,d2
ext.l d2
move.w ButtHeight,d3
ext.l d3
lea dbb_TagList2,a1
movea.l GadtoolsBase,a6
movem.l d0/d1/a0/a1,-(sp) ;(-)
move.w #mgg_NumOfRecessed-1,d7
moveq #0,d6
.loopr movem.l (sp),d0/d1/a0/a1 ;restore damaged regs.
move.l (mgg_EmptyRecessed,a5,d6.w),(rp_BitMap,a3) ;set bitmap
jsr (_LVODrawBevelBoxA,a6) ;draw to my bitmap
addq.w #4,d6 ;next bmap
dbra d7,.loopr
movem.l (sp)+,d0/d1/a0/a1 ;(+)
;3. 4. 5. Flag, NoFlag, Bomb,Blowed bomb
;*Copy each gfx from it's bmap to "(mgg_xxxx,a5) bmap"
;first fill the background with EXTRABACKCOLOR
movea.l MGGfx,a5
movea.l _GfxBase,a6
movea.l a3,a1 ;rp
moveq #EXTRABACKCOLOR,d0
jsr (_LVOSetAPen,a6)
moveq #2,d0
moveq #1,d1
move.w ButtWidth,d2
subq.w #3,d2
ext.l d2
move.w ButtHeight,d3
subq.w #2,d3
ext.l d3
movem.l d0/d1,-(sp) ;(-)
move.l (mgg_Flag,a5),(rp_BitMap,a3)
movea.l a3,a1
jsr (_LVORectFill,a6)
movem.l (sp),d0/d1
move.l (mgg_NoFlag,a5),(rp_BitMap,a3)
movea.l a3,a1
jsr (_LVORectFill,a6)
movem.l (sp),d0/d1
move.l (mgg_Bomb,a5),(rp_BitMap,a3)
movea.l a3,a1
jsr (_LVORectFill,a6)
tst.b ([MyPrefs],mprf_GfxType)
beq.s .std
moveq #BLOWEDBACKMAG,d0
bra.s .000
.std moveq #BLOWEDBACKSTD,d0
.000 movea.l a3,a1 ;rp
jsr (_LVOSetAPen,a6)
movem.l (sp),d0/d1
move.l (mgg_Blowed,a5),(rp_BitMap,a3)
movea.l a3,a1
jsr (_LVORectFill,a6)
movem.l (sp)+,d0/d1 ;(+)
tst.b ([MyPrefs],mprf_ScaleGfx)
beq.s .notscale
;*****scale bitmaps
lea bitScaleArgs,a0
clr.w (bsa_SrcX,a0)
clr.w (bsa_SrcY,a0)
move.w #2,(bsa_DestX,a0)
move.w #1,(bsa_DestY,a0)
move.w #BUTMINX,(bsa_SrcWidth,a0)
move.w #BUTMINY,(bsa_SrcHeight,a0)
clr.l (bsa_Flags,a0)
;get denominators and numerators
;WIDTH
move.w ButtWidth,d0
move.w #BUTMINX,d1
subq.w #4,d0 ;dest. width
move.l #16383,d2
divu.w d0,d2
mulu.w d2,d0 ;x-numerator
mulu.w d2,d1 ;x-denominator
move.w d0,(bsa_XDestFactor,a0)
move.w d1,(bsa_XSrcFactor,a0)
;HEIGHT
move.w ButtHeight,d0
move.w #BUTMINY,d1
subq.w #2,d0 ;dest. height
move.l #16383,d2
divu.w d0,d2
mulu.w d2,d0 ;y-numerator
mulu.w d2,d1 ;y-denominator
move.w d0,(bsa_YDestFactor,a0)
move.w d1,(bsa_YSrcFactor,a0)
;--Flag
; lea bitScaleArgs,a0
move.l #bmapFlag,(bsa_SrcBitMap,a0) ;SrcBitMap
movea.l (mgg_Flag,a5),(bsa_DestBitMap,a0) ;DstBitBap
jsr (_LVOBitMapScale,a6)
;--NoFlag
lea bitScaleArgs,a0
move.l #bmapNoFlag,(bsa_SrcBitMap,a0) ;SrcBitMap
movea.l (mgg_NoFlag,a5),(bsa_DestBitMap,a0) ;DstBitBap
jsr (_LVOBitMapScale,a6)
;--Bomb
lea bitScaleArgs,a0
move.l #bmapBomb,(bsa_SrcBitMap,a0) ;SrcBitMap
movea.l (mgg_Bomb,a5),(bsa_DestBitMap,a0) ;DstBitBap
jsr (_LVOBitMapScale,a6)
;--Blowed
lea bitScaleArgs,a0
move.l #bmapBlowed,(bsa_SrcBitMap,a0) ;SrcBitMap
movea.l (mgg_Blowed,a5),(bsa_DestBitMap,a0) ;DstBitBap
jsr (_LVOBitMapScale,a6)
bra.s .skipnotscale
.notscale ;center gfx in dest bitmap
move.w ButtWidth,d2
asr.w #1,d2 ;/2
move.w #BUTMINX,d0
move.w d0,d4 ;size x
asr.w #1,d0
sub.w d0,d2 ;dest x
move.w ButtHeight,d3
asr.w #1,d3
move.w #BUTMINY,d0
move.w d0,d5 ;size y
asr.w #1,d0
sub.w d0,d3 ;dest y
ext.l d2 ;to follow recommendations
ext.l d3
ext.l d4
ext.l d5
moveq #0,d0 ;sour x
move.l d0,d1 ;sour y
move.l #$c0,d6 ;miniterm
moveq #-1,d7 ;mask
suba.l a2,a2 ;TempA
movem.l d0/d1,-(sp) ;store (-)
lea bmapFlag,a0 ;SrcBitMap
movea.l (mgg_Flag,a5),a1 ;DstBitBap
jsr (_LVOBltBitMap,a6)
movem.l (sp),d0/d1 ;restore damaged regs.
lea bmapNoFlag,a0 ;SrcBitMap
movea.l (mgg_NoFlag,a5),a1 ;DstBitBap
jsr (_LVOBltBitMap,a6)
movem.l (sp),d0/d1 ;restore damaged regs.
lea bmapBomb,a0 ;SrcBitMap
movea.l (mgg_Bomb,a5),a1 ;DstBitBap
jsr (_LVOBltBitMap,a6)
movem.l (sp),d0/d1 ;restore damaged regs.
lea bmapBlowed,a0 ;SrcBitMap
movea.l (mgg_Blowed,a5),a1 ;DstBitBap
jsr (_LVOBltBitMap,a6)
movem.l (sp)+,d0/d1 ;restore damaged regs. (+)
.skipnotscale
;**Now create number buttons
;get fonts baseline and xy-sizes
movea.l a3,a1 ;rp ;set pens
moveq #1,d0 ;pen
jsr (_LVOSetAPen,a6)
movea.l a3,a1 ;rp
moveq #0,d0
jsr (_LVOSetBPen,a6)
movea.l WinFont,a0
move.w (tf_XSize,a0),d0
asr.w #1,d0
move.w ButtWidth,d2
asr.w #1,d2
sub.w d0,d2 ;xpos
move.w (tf_YSize,a0),d0
asr.w #1,d0
move.w ButtHeight,d3
asr.w #1,d3
sub.w d0,d3
add.w (tf_Baseline,a0),d3 ;ypos
movea.l MGGfx,a5
movea.l _GfxBase,a6
moveq #8-1,d7 ;numbers 1-8
moveq #0,d6 ;offset
move.b #'1',d5 ;char
clr.w Storage
.loopt move.l (mgg_Num1,a5,d6.w),(rp_BitMap,a3)
movea.l a3,a1 ;rp
move.w d2,d0 ;x
move.w d3,d1 ;y
ext.l d0
ext.l d1
jsr (_LVOMove,a6)
moveq #1,d0 ;len
movea.l a3,a1 ;rp
lea Storage,a0 ;string
move.b d5,(a0) ;put char
jsr (_LVOText,a6)
addq.w #4,d6 ;next bitmap
addq.b #1,d5 ;next number
dbra d7,.loopt
;create questionmark
move.w d2,d4 ;store
move.w d3,d5
movea.l a3,a1 ;rp
moveq #QUESTBACKCOLOR,d0
jsr (_LVOSetAPen,a6)
moveq #2,d0
moveq #1,d1
move.w ButtWidth,d2
subq.w #3,d2
ext.l d2
move.w ButtHeight,d3
subq.w #2,d3
ext.l d3
move.l (mgg_Question,a5),(rp_BitMap,a3)
movea.l a3,a1
jsr (_LVORectFill,a6) ;fill the background
movea.l a3,a1 ;rp ;set pens
moveq #1,d0 ;pen
jsr (_LVOSetAPen,a6)
movea.l a3,a1 ;rp
moveq #QUESTBACKCOLOR,d0
jsr (_LVOSetBPen,a6)
move.l (mgg_Question,a5),(rp_BitMap,a3)
movea.l a3,a1 ;rp
move.w d4,d0 ;x
move.w d5,d1 ;y
ext.l d0
ext.l d1
jsr (_LVOMove,a6)
moveq #1,d0 ;len
movea.l a3,a1 ;rp
lea Storage,a0
clr.w (a0)
move.b #'?',(a0) ;string
jsr (_LVOText,a6)
rts
creategfx_error lea nomygfx_Text,a1
lea nomygfx_Button,a2
bsr.w InformationReq
clr.l MGGfx
rts
;*****************************************************************
FreeGfx movea.l _GfxBase,a6
jsr (_LVOWaitBlit,a6)
movea.l MGGfx,a2
moveq #GADBPLNUM-1,d2
.loop move.l (a2)+,d0 ;bitmaps
beq.s .exit
movea.l d0,a0
jsr (_LVOFreeBitMap,a6)
dbra d2,.loop
.exit rts
;*****************************************************************
PutButton ;puts a single button on x,y (d0.w/d1.w)
;d2.w = button number (e.G. mgg_Empty/4)
movea.l MGGfx,a3 ;src bitmaps
movea.l _GfxBase,a6
;check range 1..PFw/h-1
cmpi.w #1,d0
blt.w .exit
cmpi.w #1,d1
blt.w .exit
move.w d0,d4
addq.w #1,d4
cmp.w PFWidth,d4
bge.w .exit
move.w d1,d5
addq.w #1,d5
cmp.w PFHeight,d5
bge.w .exit
movea.l (a3,d2.w*4),a0 ;SrcBitMap
move.w ButtWidth,d4 ;SizeX
ext.l d4
move.w ButtHeight,d5 ;SizeY
ext.l d5
move.w d0,d2
move.w d1,d3
subq.w #1,d2
subq.w #1,d3
mulu.w d4,d2
mulu.w d5,d3
add.w MinPFX,d2 ;DstX
ext.l d2
add.w MinPFY,d3 ;DstY
ext.l d3
movea.l MyWindow,a1
movea.l (wd_RPort,a1),a1 ;DstRPort
moveq #0,d0 ;SrcX
move.l d0,d1 ;SrcY
move.l #$c0,d6 ;Minterm
jsr (_LVOBltBitMapRastPort,a6)
.exit rts
;*****************************************************************
ShowButton ;IN: d0.w = x , d1.w = y, d2.w = PF position
;NOTE: x,y,d2.w is a real position in the PF <1.. *-1>
;displays contens of first field at pos. x,y
;and if empty, seedfills whole empty area
;RETURN: d0.b - num. of button pressed (e.G. bomb)
movea.l sp,a2
move.l SeedFillSP,sp
move.l a2,-(sp)
bsr.s .go
movea.l (sp)+,sp
rts
.go movea.l MyWindow,a2
movea.l MGGfx,a3 ;src bitmaps
movea.l PFAdr,a4 ;1st field
movea.l a4,a5
adda.w PFSize,a5 ;2nd field
movea.l _GfxBase,a6
clr.b d7
.seedfill
;check range 1..PFw/h-1
cmpi.w #1,d0
blo.w .exit
cmpi.w #1,d1
blo.w .exit
move.w d0,d4
addq.w #1,d4
cmp.w PFWidth,d4
bhs.w .exit
move.w d1,d5
addq.w #1,d5
cmp.w PFHeight,d5
bhs.w .exit
cmpi.b #QMARK,(a5,d2.w)
bne.s .0
tst.b ([MyPrefs],mprf_DeadQ)
beq.w .exit
bra.s .deadq
.0 tst.b (a5,d2.w) ;pressed or flag?
bne.w .exit ;yes
.deadq move.b #1,(a5,d2.w) ;pressed
move.b (a4,d2.w),d7
bne.w .cont
movem.w d0/d1/d2/d7,-(sp)
sub.w PFWidth,d2 ;u
subq.w #1,d1
bsr.s .seedfill
movem.w (sp),d0/d1/d2/d7
sub.w PFWidth,d2
subq.w #1,d2 ;ul
subq.w #1,d0
subq.w #1,d1
bsr.s .seedfill
movem.w (sp),d0/d1/d2/d7
sub.w PFWidth,d2
addq.w #1,d2 ;ur
addq.w #1,d0
subq.w #1,d1
bsr.w .seedfill
movem.w (sp),d0/d1/d2/d7
subq.w #1,d2 ;l
subq.w #1,d0
bsr.w .seedfill
movem.w (sp),d0/d1/d2/d7
addq.w #1,d2 ;r
addq.w #1,d0
bsr.w .seedfill
movem.w (sp),d0/d1/d2/d7
add.w PFWidth,d2 ;d
addq.w #1,d1
bsr.w .seedfill
movem.w (sp),d0/d1/d2/d7
add.w PFWidth,d2
subq.w #1,d2 ;dl
addq.w #1,d1
subq.w #1,d0
bsr.w .seedfill
movem.w (sp),d0/d1/d2/d7
add.w PFWidth,d2
addq.w #1,d2 ;dr
addq.w #1,d1
addq.w #1,d0
bsr.w .seedfill
movem.w (sp)+,d0/d1/d2/d7
.cont subq.w #1,WinCount
ext.w d7
movea.l (a3,d7.w*4),a0 ;SrcBitMap
move.w ButtWidth,d4 ;SizeX
ext.l d4
move.w ButtHeight,d5 ;SizeY
ext.l d5
move.w d0,d2
move.w d1,d3
subq.w #1,d2
subq.w #1,d3
mulu.w d4,d2
mulu.w d5,d3
add.w MinPFX,d2 ;DstX
ext.l d2
add.w MinPFY,d3 ;DstY
ext.l d3
movea.l (wd_RPort,a2),a1 ;DstRPort
moveq #0,d0 ;SrcX
move.l d0,d1 ;SrcY
move.l #$c0,d6 ;Minterm
jsr (_LVOBltBitMapRastPort,a6)
.exit
move.b d7,d0
rts
;*****************************************************************
ClearWin movea.l _GfxBase,a6
movea.l MyWindow,a0
movea.l (wd_RPort,a0),a1
move.w MinX,d0
ext.l d0
move.w MinY,d1
ext.l d1
move.w d0,d2
add.w InnWidth,d2
subq.w #1,d2
ext.l d2
move.w d1,d3
add.w InnHeight,d3
subq.w #1,d3
ext.l d3
jsr (_LVOEraseRect,a6) ;clear
rts
;*****************************************************************
RedrawMainBar bsr.w RedrawGadget
;**get new Time and BCount display positions
move.w MinX,d0
add.w InnWidth,d0
subi.w #NUMBBOXX+NUMDISTANCE,d0
move.w d0,TimeX
move.w MyBarHeight,d0
asr.w #1,d0 ;/2
add.w MinY,d0
subi.w #NUMBBOXY/2,d0
move.w d0,TimeY
move.w d0,BCountY
move.w MinX,d0
addq.w #NUMDISTANCE,d0
move.w d0,BCountX
;**redraw time and bombs (0)
move.w TimeX,d0
move.w TimeY,d1
move.w MyTime+2,d2
bsr.w DrawNumber
move.w BCountX,d0
move.w BCountY,d1
move.w BCount,d2
bsr.w DrawNumber
rts
;*****************************************************************
RedrawWindow ;IN: d0-type of redrawing (BYTE)
tst.b Disable ;is window o.k.?
bne.w ClearWin
move.w d0,-(sp)
bsr.w RedrawMainBar
move.w (sp)+,d0
tst.b Pause
bne.s .ret
pea (.ret,pc)
cmpi.b #RW_START,d0
beq.s redrStart
cmpi.b #RW_END,d0
beq.w redrEnd
cmpi.b #RW_ACTUAL,d0
beq.w redrActual
addq.w #4,a7
.ret
rts
;------------------------------------------------------------------
redrStart
;get window position first
move.w MinPFX,d0
ext.l d0
move.w MinPFY,d1
ext.l d1
movem.l d0/d1,-(sp) ;store x and y
moveq #1,d0
move.l d0,d1
moveq #mgg_Empty/4,d2
bsr.w PutButton ;put the first button
movea.l _GfxBase,a6
movea.l MyWindow,a0
movea.l (wd_RPort,a0),a3
suba.l a2,a2 ;TempA
;fill the first line (x steps)
movea.w PFWidth,a4 ;required buttons to complete x
subq.w #2,a4
movea.w #2,a5 ;already completed
movem.l (sp),d2/d3 ;destx/desty
add.w ButtWidth,d2 ;destx
ext.l d2
move.w ButtWidth,d4 ;sizex
ext.l d4
move.w ButtHeight,d5 ;sizey
ext.l d5
move.l #$c0,d6 ;miniterm
.nextx movem.l (sp),d0/d1 ;start position
;(always upper left corner of the window)
movea.l a3,a0 ;source and dest. bmap
movea.l a3,a1
jsr (_LVOClipBlit,a6)
add.l d4,d4 ;sizex*2
move.l d4,d2 ;destx
add.l (sp),d2 ;(+win. offset)
adda.w a5,a5
cmpa.w a5,a4
bhs.s .nextx
move.w a5,d4
asr.w #1,d4
move.w d4,d2
ext.l d4
mulu.w ButtWidth,d2 ;destx
add.l (sp),d2
neg.l d4
add.l a4,d4 ;get the rest of buttons
beq.s .xcomplete
mulu.w ButtWidth,d4 ;sizex
movem.l (sp),d0/d1
movea.l a3,a0
movea.l a3,a1
jsr (_LVOClipBlit,a6)
.xcomplete ;**now do similar with y blocks
movea.w PFHeight,a4 ;required lines to complete y
subq.w #2,a4
movea.w #2,a5 ;already completed
movem.l (sp),d2/d3 ;destx/desty
add.w ButtHeight,d3 ;desty
ext.l d3
move.w PFWidth,d4 ;sizex
subq.w #2,d4
mulu.w ButtWidth,d4 ;&
move.w ButtHeight,d5 ;sizey
ext.l d5
.nexty movem.l (sp),d0/d1 ;start position
;(always upper left corner of the window)
movea.l a3,a0 ;source and dest. bmap
movea.l a3,a1
jsr (_LVOClipBlit,a6)
add.l d5,d5 ;sizey*2
move.l d5,d3 ;desty
add.l (4,sp),d3
adda.w a5,a5
cmpa.w a5,a4
bhs.s .nexty
move.w a5,d5
asr.w #1,d5
move.w d5,d3
ext.l d5
mulu.w ButtHeight,d3 ;desty
add.l (4,sp),d3
neg.l d5
add.l a4,d5 ;get the rest of lines
beq.s .ycomplete
mulu.w ButtHeight,d5 ;sizey
movem.l (sp),d0/d1
movea.l a3,a0
movea.l a3,a1
jsr (_LVOClipBlit,a6)
.ycomplete
addq.l #8,sp ;restore stack
rts
;----------------------------------------------------------------
redrEnd ;**draw contens of the PlayField
move.w MinPFX,d2 ;DstX
ext.l d2
move.w MinPFY,d3 ;DstY
ext.l d3
move.w ButtWidth,d4 ;SizeX
ext.l d4
move.w ButtHeight,d5 ;SizeY
ext.l d5
movea.l MGGfx,a3 ;src bitmaps
movea.l MyWindow,a4
movea.l (wd_RPort,a4),a4 ;dst
movea.l PFAdr,a5 ;PF contens
adda.w PFWidth,a5 ;pos 1,1
addq.w #1,a5 ;&
movea.l _GfxBase,a6
move.w PFHeight,d7
subq.w #2+1,d7
.heightloop move.w PFWidth,d6
subq.w #2+1,d6
.widthloop
movem.w d6/d7,-(sp)
;copy bitmap
move.w PFSize,d7
move.b (a5,d7.w),d7
move.b (a5)+,d6
cmpi.b #mgg_Blowed/4,d6
beq.s .next
cmpi.b #mgg_Bomb/4,d6
bne.s .flag
cmpi.b #FLAG,d7
beq.s .next
tst.b Win
beq.s .flok
move.b #mgg_Flag/4,d6
bra.s .flok
.flag cmpi.b #FLAG,d7
bne.s .next
move.b #mgg_NoFlag/4,d6
.flok
ext.w d6
movea.l (a3,d6.w*4),a0 ;SrcBitMap
moveq #0,d0 ;SrcX
move.l d0,d1 ;SrcY
movea.l a4,a1 ;DstRPort
move.l #$c0,d6 ;Minterm
jsr (_LVOBltBitMapRastPort,a6)
.next add.l d4,d2
movem.w (sp)+,d6/d7
dbra d6,.widthloop
add.l d5,d3
addq.w #2,a5
move.w MinPFX,d2
ext.l d2
dbra d7,.heightloop
rts
;---------------------------------------------------------------
redrActual
move.w MinPFX,d2 ;DstX
ext.l d2
move.w MinPFY,d3 ;DstY
ext.l d3
move.w ButtWidth,d4 ;SizeX
ext.l d4
move.w ButtHeight,d5 ;SizeY
ext.l d5
movea.l MGGfx,a3 ;src bitmaps
movea.l MyWindow,a4
movea.l (wd_RPort,a4),a4 ;dst
movea.l PFAdr,a5 ;PF contens
movea.l a5,a2
adda.w PFSize,a2
adda.w PFWidth,a5 ;pos 1,1
addq.w #1,a5 ;&
adda.w PFWidth,a2 ;pos 1,1
addq.w #1,a2 ;&
movea.l _GfxBase,a6
move.w PFHeight,d7
subq.w #2+1,d7
.heightloop move.w PFWidth,d6
subq.w #2+1,d6
.widthloop
move.w d6,-(sp)
;copy bitmap
cmpi.b #FLAG,(a2)
bne.s .noflag
movea.l (mgg_Flag,a3),a0
bra.s .draw
.noflag cmpi.b #QMARK,(a2)
bne.s .noqmark
movea.l (mgg_Question,a3),a0
bra.s .draw
.noqmark tst.b (a2) ;pressed?
bne.s .yes ;yes
movea.l (mgg_Empty,a3),a0
bra.s .draw
.yes move.b (a5),d6
ext.w d6
movea.l (a3,d6.w*4),a0 ;SrcBitMap
.draw addq.w #1,a2
addq.w #1,a5
moveq #0,d0 ;SrcX
move.l d0,d1 ;SrcY
movea.l a4,a1 ;DstRPort
move.l #$c0,d6 ;Minterm
jsr (_LVOBltBitMapRastPort,a6)
add.l d4,d2
move.w (sp)+,d6
dbra d6,.widthloop
add.l d5,d3
addq.w #2,a5
addq.w #2,a2
move.w MinPFX,d2
ext.l d2
dbra d7,.heightloop
rts
;*****************************************************************
ResizeWindow ;**change box
bsr.w SetWinParams
bsr.w RemSunG
lea SunGadget,a0
move.l #0,(gg_GadgetRender,a0)
move.l #0,(gg_SelectRender,a0)
bsr.w AddSunG
bsr.w ClearWin
;**Change the window box
movea.l IntuiBase,a6
movea.l MyWindow,a0
move.w WinX,d0
ext.l d0
move.w WinY,d1
ext.l d1
move.w WinWidth,d2
ext.l d2
move.w WinHeight,d3
ext.l d3
jsr (_LVOChangeWindowBox,a6)
st IDidTheChange
rw_exit rts
;*****************************************************************
RedrawGadget bsr.s RemSunG
movea.l IntuiBase,a6
movea.l MyWindow,a0
jsr (_LVORefreshWindowFrame,a6)
; no rts !!
AddGadget
;IN:Gadget_Image.l gadget image
lea SunGadget,a0 ;set new position of the gadget
move.w InnWidth,d0
subi.w #SUNMINX,d0
asr.w #1,d0
add.w MinX,d0
move.w d0,(gg_LeftEdge,a0)
move.w MyBarHeight,d0
subi.w #SUNMINY,d0
asr.w #1,d0
add.w MinY,d0
move.w d0,(gg_TopEdge,a0)
;set appropriate gadget image
tst.b Disable
beq.s .norm
clr.l (gg_GadgetRender,a0)
clr.l (gg_SelectRender,a0)
bra.s .dis
.norm move.l Gadget_Image,(gg_GadgetRender,a0)
move.l #img_SunPressed,(gg_SelectRender,a0)
.dis bsr.s AddSunG
movea.l IntuiBase,a6
lea SunGadget,a0
movea.l MyWindow,a1
suba.l a2,a2
jsr (_LVORefreshGadgets,a6)
rts
;---------------------------
RemSunG movea.l IntuiBase,a6
movea.l MyWindow,a0
lea SunGadget,a1
jsr (_LVORemoveGadget,a6) ;I'm not able to handle errors
rts
AddSunG movea.l IntuiBase,a6
moveq #0,d0
movea.l MyWindow,a0
lea SunGadget,a1
jsr (_LVOAddGadget,a6)
rts
;*****************************************************************
ChangeIDCMP ;IN: d0 - idcmp flags
movea.l IntuiBase,a6
movea.l MyWindow,a0
move.l OldIDCMP,d2
eor.l d2,d0
move.l d0,d2
jsr (_LVOModifyIDCMP,a6)
tst.l d0
beq.s .fail
move.l d2,OldIDCMP
.fail rts
;*****************************************************************
OpenMyWindow
;**Open MyWindow
movea.l IntuiBase,a6
suba.l a0,a0 ;NewWindow=0
lea MyWinTags,a1 ;TagList
jsr (_LVOOpenWindowTagList,a6)
move.l d0,MyWindow
bne.s .cont
lea nowin_Text,a1
lea nowin_Button,a2
bsr.w InformationReq
bra.s .nowindow
.cont
;*set new window pointer for ReqTools requesters
move.l MyWindow,d0
move.l d0,IReqTags+12
move.l d0,JoinGetTags+4
move.l d0,GSReqTags+4
move.l d0,HiScoresTags+4
;**set font
move.l WinFont,d0
beq.s .skip
movea.l _GfxBase,a6
movea.l d0,a0 ;font
movea.l MyWindow,a1
movea.l (wd_RPort,a1),a1 ;rp
jsr (_LVOSetFont,a6)
.skip
.nowindow rts
;----------------------------------------------------------
CloseMyWindow movea.l (EB,PC),a6
movea.l Semaphore,a0
jsr (_LVOObtainSemaphore,a6)
;**collect all possible pending messages
movea.l MyWindow,a2
move.l (wd_UserPort,a2),d2
beq.s .noport
.cl movea.l d2,a0
jsr (_LVOGetMsg,a6)
tst.l d0
bne.s .cl
moveq #0,d0
clr.l OldIDCMP
bsr.w ChangeIDCMP ;close IDCMP ports
.noport
movea.l (EB,PC),a6
movea.l Semaphore,a0
jsr (_LVOReleaseSemaphore,a6)
movea.l IntuiBase,a6
movea.l MyWindow,a0
jsr (_LVOCloseWindow,a6)
;*set zero pointer for ReqTools requesters
moveq #0,d0
move.l d0,IReqTags+12
move.l d0,JoinGetTags+4
move.l d0,GSReqTags+4
move.l d0,HiScoresTags+4
rts
;**********************************************************************
OpenMyScreen
;**Check settings
movea.l MyPrefs,a0
tst.b (mprf_CustomScreen,a0) ;customscreen=yes?
beq.w noscreen
;set tags
lea MyScreenTags,a1
tagloop move.l (a1)+,d0
cmpi.l #TAG_DONE,d0
beq.w tags_done
cmpi.l #SA_Width,d0
beq.s .setWidth
cmpi.l #SA_Height,d0
beq.s .setHeight
cmpi.l #SA_DisplayID,d0
beq.s .setModeID
cmpi.l #SA_LikeWorkbench,d0
beq.s .wblike
addq.w #4,a1 ;just other tag
bra.s tagloop
.setWidth move.w (mprf_ScrWidth,a0),d0
ext.l d0
bne.s .0
move.l #STDSCREENWIDTH,d0
.0 move.l d0,(a1)+
bra.s tagloop
.setHeight move.w (mprf_ScrHeight,a0),d0
ext.l d0
bne.s .1
move.l #STDSCREENHEIGHT,d0
.1 move.l d0,(a1)+
bra.s tagloop
.setModeID move.l (mprf_ModeID,a0),d0
bne.s .2
move.l #PAL_MONITOR_ID!HIRES_KEY,d0
move.l d0,(mprf_ModeID,a0)
.2 move.l d0,(a1)+
bra.w tagloop
.wblike tst.b (mprf_WBLike,a0)
bne.s .wbl
move.l #FALSE,(a1)+
bra.s tagloop
.wbl move.l #TRUE,(a1)+
move.l #TAG_DONE,(a1)
tags_done
;**Open screen
movea.l IntuiBase,a6
suba.l a0,a0 ;NewScreen
lea MyScreenTags,a1
jsr (_LVOOpenScreenTagList,a6)
move.l d0,MyScreen
bne.s .ok
lea NoScr_Text,a1
lea NoScr_Button,a2
bsr.w InformationReq
clr.b ([MyPrefs],mprf_CustomScreen)
.ok
noscreen rts
;*******
CloseMyScreen movea.l IntuiBase,a6
movea.l MyScreen,a0
movea.l MyDrawInfo,a1
jsr (_LVOFreeScreenDrawInfo,a6)
tst.b ([MyPrefs],mprf_CustomScreen)
bne.s .cust
suba.l a0,a0
movea.l MyScreen,a1
jsr (_LVOUnlockPubScreen,a6)
bra.s .exit
.cust
movea.l MyScreen,a0
jsr (_LVOCloseScreen,a6)
.exit rts
;*****************************************************************
SetPalette
tst.b ([MyPrefs],mprf_CustomScreen)
beq.s .exit
movea.l MyScreen,a0
;**Set palette here
movea.l _GfxBase,a6
lea (sc_ViewPort,a0),a0
lea ScreenPalette,a1 ;palette
jsr (_LVOLoadRGB32,a6) ;load 8-bit palette
.exit rts
;*****************************************************************
OpenFont movea.l MyPrefs,a2
lea MyTextAttr,a3
move.l (mprf_FontName,a2),(ta_Name,a3) ;font name
beq.s .setdefault
move.w (mprf_FontSize,a2),(ta_YSize,a3) ;font size
bne.s .sizeok ;if Size=0 then set other size
;**use the designed font
move.b #FPF_DESIGNED,(ta_Flags,a3)
.sizeok
;**try diskfont
movea.l (EB,PC),a6
moveq #0,d0
lea DiskFontName,a1
jsr (_LVOOpenLibrary,a6)
move.l d0,Storage
beq.s .rom
movea.l d0,a6 ;library base
movea.l a3,a0 ;TTextAttr
jsr (_LVOOpenDiskFont,a6)
move.l d0,WinFont
movea.l (EB,PC),a6
movea.l Storage,a1 ;diskfont.library base
jsr (_LVOCloseLibrary,a6)
tst.l WinFont
bne.s .exit
.rom movea.l _GfxBase,a6
movea.l a3,a0 ;TextAttr
jsr (_LVOOpenFont,a6)
move.l d0,WinFont
bne.s .exit
lea nofont_Text,a1
lea nofont_Button,a2
bsr.w InformationReq
.setdefault movea.l _GfxBase,a0
move.l (gb_DefaultFont,a0),WinFont
clr.l ([MyPrefs],mprf_FontName)
rts
.exit
move.l ([WinFont],LN_NAME),([MyPrefs],mprf_FontName)
rts
CloseFont move.l WinFont,d0
beq.s .exit
movea.l _GfxBase,a6
movea.l d0,a1
jsr (_LVOCloseFont,a6)
.exit rts
;*****************************************************************
FontToRT movea.l _GfxBase,a6
movea.l (gb_DefaultFont,a6),a0
lea MyTextAttr,a1
move.l (LN_NAME,a0),(a1) ;LN_NAME -> ta_Name
move.w (tf_YSize,a0),(ta_YSize,a1)
move.b (tf_Style,a0),(ta_Style,a1)
move.b (tf_Flags,a0),(ta_Flags,a1)
rts
;*****************************************************************
GetDRI ;**get screen draw info
movea.l IntuiBase,a6
movea.l MyScreen,a0
jsr (_LVOGetScreenDrawInfo,a6)
move.l d0,MyDrawInfo
rts
;*****************************************************************
LockScreen movea.l IntuiBase,a6
tst.l MyScreen
bne.s nolock
move.l ([MyPrefs],mprf_PubNameAdr),d0 ;any public screen specified?
beq.s .wb ;no
movea.l d0,a0 ;$ check if it's open
jsr (_LVOLockPubScreen,a6)
tst.l d0
bne.s .gotone ;$ yes it is
clr.l ([MyPrefs],mprf_PubNameAdr)
.wb suba.l a0,a0 ;Workbench or default public screen
jsr (_LVOLockPubScreen,a6)
.gotone move.l d0,MyScreen
nolock rts
;*****************************************************************
SetMenu
;Create NewMenu structure for gadtools.library
lea MyMenu,a0
lea GTNewMenu,a1
.copy move.b (mmi_Type,a0),d0
beq.w .copied
move.b d0,(gnm_Type,a1)
move.w (mmi_Flags,a0),(gnm_Flags,a1)
move.l (mmi_CommKey,a0),(gnm_CommKey,a1)
move.l (mmi_Mutual,a0),(gnm_MutualExclude,a1)
move.l (mmi_Name,a0),(gnm_Label,a1)
lea (mmi_SIZEOF,a0),a0
lea (gnm_SIZEOF,a1),a1
bra.s .copy
.copied
movea.l GadtoolsBase,a6
lea GTNewMenu,a0
lea NewMenuTags,a1
jsr (_LVOCreateMenusA,a6)
move.l d0,MenuStruct
beq.s NoMenu
movea.l MenuStruct,a0
movea.l VisualInfo,a1
lea LayoutTags,a2
jsr (_LVOLayoutMenusA,a6)
tst.l d0
beq.s NoMenu2
;Hey! set it finally!
movea.l IntuiBase,a6
movea.l MyWindow,a0
movea.l MenuStruct,a1
jsr (_LVOSetMenuStrip,a6)
;set checkmark due to level
move.b ([MyPrefs],mprf_Level),d0
subq.b #1,d0
ext.w d0
mulu.w #mmi_SIZEOF,d0
lea LevelItems,a0
move.w (mmi_Code,a0,d0.w),d0
ext.l d0 ;to be sure
movea.l IntuiBase,a6
movea.l MenuStruct,a0
jsr (_LVOItemAddress,a6)
movea.l d0,a0
ori.w #CHECKED,(mi_Flags,a0) ;set checkmark
rts
NoMenu2 movea.l MenuStruct,a0
jsr (_LVOFreeMenus,a6)
NoMenu clr.l MenuStruct
lea nomenu_Text,a1
lea nomenu_Button,a2
bsr.w InformationReq
rts
;-------------------------------------------------------
ClearMenu tst.l MenuStruct
beq.s .nomenu
movea.l IntuiBase,a6
movea.l MyWindow,a0
jsr (_LVOClearMenuStrip,a6)
movea.l GadtoolsBase,a6
movea.l MenuStruct,a0
jsr (_LVOFreeMenus,a6)
.nomenu rts
;*****************************************************************
InformationReq ;IN: a1 - text a2 - button text
movem.l d1-d7/a0-a6,-(sp)
movea.l _ReqToolsBase,a6
suba.l a3,a3
suba.l a4,a4
lea IReqTags,a0
jsr (_LVOrtEZRequestA,a6)
movem.l (sp)+,d1-d7/a0-a6
rts
;*****************************************************************
CDProggy movea.l DosBase,a6
move.l ProgDir,d1
jsr (_LVOCurrentDir,a6)
lea (olddir,pc),a0
move.l d0,(a0)
rts
CDBack movea.l DosBase,a6
move.l (olddir,pc),d1
jsr (_LVOCurrentDir,a6)
rts
olddir dc.l 0
;*****************************************************************
;---------------------------------------------------
HEADSIZE = 25
LINESIZE = 12+NAMELEN+9
LEVELSIZE = LINESIZE*2
CUSTOMSIZE = LEVELSIZE+6*28
HS_TEXTMEM = HEADSIZE+LEVELSIZE*4+LINESIZE+CUSTOMSIZE+1
MakeHighScores ;IN: nothing
;Makes a text string for ReqTools
movea.l MyPrefs,a5
lea HiScoresText,a0
move.w #HS_TEXTMEM-2,d7
lea (hs_ScoresText,pc),a1
lea (hs_DataTable,pc),a3
cploop move.b (a1)+,d0
cmpi.b #'$',d0
beq.s .writename
cmpi.b #'%',d0
beq.s .writenumber
move.b d0,(a0)+
dbeq d7,cploop
bra.s hs_AllDone
.writename move.b (a1)+,d0 ;get offset in table
ext.w d0
move.w (a3,d0.w*2),d0 ;get real offset
movea.l a5,a4 ;MyPrefs
moveq #0,d1 ;pocet pismen
.wnloop0 move.b (a4,d0.w),(a0)+
beq.s .wndone0
addq.l #1,a4
addq.w #1,d1
subq.w #1,d7
bmi.s hs_AllDone
bra.s .wnloop0
.wndone0 subq.l #1,a0
move.w #NAMELEN+4,d2
sub.w d1,d2
subq.w #1,d2
.wnloop1 move.b #'.',(a0)+
subq.w #1,d7
bmi.s hs_AllDone
dbra d2,.wnloop1
bra.s cploop
.writenumber move.b (a1)+,d0
ext.w d0
move.w (a3,d0.w*2),d0
move.w (a5,d0.w),d2 ;time from hiscores
bsr.w Num2String4
moveq #4-1,d2
.nloop move.b (a2)+,(a0)+
subq.w #1,d7
bmi.s hs_AllDone
dbra d2,.nloop
bra.s cploop
hs_AllDone clr.b (a0)+
rts
hs_DataTable dc.w mhs_EasyName1,mhs_EasyTime1,mhs_EasyName2,mhs_EasyTime2
dc.w mhs_NormalName1,mhs_NormalTime1,mhs_NormalName2,mhs_NormalTime2
dc.w mhs_HardName1,mhs_HardTime1,mhs_HardName2,mhs_HardTime2
dc.w mhs_ProfiName1,mhs_ProfiTime1,mhs_ProfiName2,mhs_ProfiTime2
dc.w mhs_CustomName1,mhs_CustomTime1,mhs_CustomWidth1,mhs_CustomHeight1,mhs_CustomBombs1
dc.w mhs_CustomName2,mhs_CustomTime2,mhs_CustomWidth2,mhs_CustomHeight2,mhs_CustomBombs2
hs_ScoresText dc.b '**** Best sweepers ****',10
dc.b 'Easy : 1. $',0,'%',1,10
dc.b ' 2. $',2,'%',3,10
dc.b 'Medium : 1. $',4,'%',5,10
dc.b ' 2. $',6,'%',7,10
dc.b 'Hard : 1. $',8,'%',9,10
dc.b ' 2. $',10,'%',11,10
dc.b 'Profi : 1. $',12,'%',13,10
dc.b ' 2. $',14,'%',15,10
dcb.b LINESIZE-1,'-'
dc.b 10
dc.b 'Custom : 1. $',16,'%',17,10
dc.b ' Width : %',18,10
dc.b ' Height: %',19,10
dc.b ' Mines : %',20,10
dc.b ' 2. $',21,'%',22,10
dc.b ' Width : %',23,10
dc.b ' Height: %',24,10
dc.b ' Mines : %',25
dc.b 0
cnop 0,4
;*****************************************************************
ClearHighScores ;IN: a0-MyPrefs
; MinesHiScores structure
; will be filled with defaults (Nobody 9999)
st (mhs_Valid,a0)
st (mhs_NewHiscore,a0)
;**set best times to default
lea (mhs_BestTimes,a0),a1
move.w #(mhs_BTEnd-mhs_BestTimes)/2-1,d0
.time move.w #MAXTIME,(a1)+
dbra d0,.time
;**clear all names
lea (mhs_BestNames,a0),a1
move.w #(mhs_BNEnd-mhs_BestNames)/NAMELEN-1,d0
.cp0 clr.b (a1)
lea (NAMELEN,a1),a1
dbra d0,.cp0 ;next
clr.l (mhs_CustomWidth1,a0) ;1.w,2.w
clr.l (mhs_CustomHeight1,a0)
clr.l (mhs_CustomBombs1,a0)
rts
;*****************************************************************
DSIZEW = (mhs_SIZEOF-mhs_Data)/2
GETC MACRO ;CHAR,ADD
cmpi.b #\1,d0
bne.s .0\@
move.b (a0)+,d0
subq.w #1,d1
addi.b #\2,d0
bra.s .ok
.0\@
ENDM
GetMHS ;decode file and extract MinesHiScores structure
;IN: d1 = (FileLenght - 1) , a5 = filebuffer
; a4 = MyPrefs
;convert text->zmatky
movea.l a5,a0 ;src
movea.l a5,a1 ;dest
moveq #0,d2 ;lenght
;kill LF
move.w d1,d3
.lfloop move.b (a0)+,d0
cmpi.b #10,d0
bne.s .nolf
subq.w #1,d1
bra.s .lfok
.nolf move.b d0,(a1)+
.lfok dbra d3,.lfloop
tst.w d1
bmi.s .empty
movea.l a5,a0 ;src
movea.l a5,a1 ;dest
.loop move.b (a0)+,d0
subq.w #1,d1
bmi.s .ok
GETC LOWC,-32
GETC MEDC,127-32
GETC HIGHC,222-32
move.l d0,d0
.ok move.b d0,(a1)+
addq.w #1,d2
tst.w d1
bpl.s .loop
.empty
cmpi.l #hsf_SIZEOF,d2 ;lenght ok?
bne.s .error
movea.l a5,a0 ;file addr
;check coded checksum
move.w #DSIZEW-1,d3
moveq #0,d0
lea (hsf_Data,a0),a0
.chck add.w (a0)+,d0
dbra d3,.chck
cmp.w (hsf_CodedChecksum,a5),d0
bne.s .error
;encode
move.l (a5),d2 ;RndSeed
lea (hsf_Data,a5),a0
move.w #DSIZEW*2,d1
bsr.w Decrypt ;IN: a0-data, d1-length, d2-RndSeed
;check encoded checksum
move.w #DSIZEW-1,d3
moveq #0,d0
lea (hsf_Data,a5),a0
.chck2 add.w (a0)+,d0
dbra d3,.chck2
cmp.w (hsf_DecodedChecksum,a5),d0
bne.s .error
;O.K. the file seems to be correct so fill it to MinesHiScores struct.
move.w #DSIZEW-1,d3
lea (hsf_Data,a5),a0
movea.l a4,a1 ;MyPrefs
st (mhs_Valid,a1) ;hi-scores are valid
lea (mhs_Data,a1),a1
.cp move.w (a0)+,(a1)+
dbra d3,.cp
moveq #0,d0
rts
.error moveq #-1,d0
rts
;-----------------------------------------------------------
LoadHiScores
bsr.w CDProggy ;change directory to program
move.l #HsFileName,d0
bsr.w LOAD_FILE ;IN:d0-filename ;OUT: d0-adr. or 0 ;d1- len
tst.l d0 ;store
beq.s .skip
lea (fb,pc),a0 ;store buffer
move.l d0,(a0)
bfclr d1{0:16}
bne.s .empty ;well, too big
subq.w #1,d1 ;file lenght
bmi.s .empty ;empty file
movea.l d0,a5
movea.l MyPrefs,a4
bsr.w GetMHS
tst.b d0 ;error?
bne.s .hsc_CrapFile
move.w (hsf_LastXmasYear,a5),LastXmas ;get last xmas
.empty
.crapret movea.l (fb,pc),a1 ;file buffer
bsr.w FreeMemBlock
.skip movea.l MyPrefs,a0
clr.b (mhs_NewHiscore,a0)
tst.b (mhs_Valid,a0) ;hi-scores loaded correctly?
bne.s .hsok
bsr.w ClearHighScores ;no
.hsok
bsr.w CDBack
rts
.hsc_CrapFile lea (crap_Text,pc),a1
lea (crap_Button,pc),a2
bsr.w InformationReq
bra.s .crapret
fb dc.l 0
crap_Text dc.b '"Mines.hiscores" is crap.',10
dc.b 'Will be overwritten on exit!',0
crap_Button dc.b 'I see..',0
cnop 0,4
;*****************************************************************
CPL = 80 ;chars per line
LOWC = '¤'
MEDC = 'ò'
HIGHC = 'Ô'
PUTCH MACRO
move.b \1,(a1)+
addq.w #1,d3
subq.w #1,d2
bne.s .cont\@
addq.w #1,d3
move.w #CPL,d2
move.b #10,(a1)+
.cont\@
ENDM
;------------------------------------------------------
SaveScore ;IN: a3 - filename ;a4 - MyPrefs
;OUT: d0 - 0=OK
;alloc buffer
move.l #hsf_SIZEOF,d0
moveq #0,d1
bsr.w ADDALLOC
tst.l d0
beq.w ss_fail
movea.l d0,a5
;copy structure to buffer
movea.l a4,a0
lea (mhs_Data,a0),a0
movea.l a5,a1
lea (hsf_Data,a1),a1
move.w #DSIZEW-1,d0
.cp move.w (a0)+,(a1)+
dbra d0,.cp
;set EncodedChecksum
movea.l a5,a0
lea (hsf_Data,a0),a0
moveq #0,d0
move.w #DSIZEW-1,d1
.chck add.w (a0)+,d0
dbra d1,.chck
move.w d0,(hsf_DecodedChecksum,a5)
;set rndseed
movea.l IntuiBase,a0
move.l (ib_Micros,a0),d2
;code
movea.l a5,a0
move.l d2,(a0) ;set rndseed to file
lea (hsf_Data,a0),a0 ;data
move.w #DSIZEW*2,d1 ;len
bsr.w Encrypt
;set coded checksum
movea.l a5,a0
lea (hsf_Data,a0),a0
moveq #0,d0
move.w #DSIZEW-1,d1
.chck2 add.w (a0)+,d0
dbra d1,.chck2
move.w d0,(hsf_CodedChecksum,a5)
move.w LastXmas,(hsf_LastXmasYear,a5)
;save
;convert zmatky->txt
;low - <0-31> med - <127-221> high - <222-255>
;chr(10) is ignored (LF)
move.l #hsf_SIZEOF,d0 ;get max. size of hi-scores file
add.l d0,d0 ;*2 for e.G. '.A'
move.l d0,d1
divu.l #CPL,d1 ;LF's
add.l d1,d0
moveq #MEMF_PUBLIC,d1
bsr.w ADDALLOC
move.l d0,d7 ;store
beq.w ss_fail
movea.l d0,a0
movea.l a0,a1
move.w #hsf_SIZEOF-1,d1
movea.l a5,a0
moveq #0,d3 ;final size
.make0 moveq #CPL,d2
.make move.b (a0)+,d0
cmpi.b #31,d0 ;check range
bhi.s .0
PUTCH #LOWC
addi.b #32,d0
.0 cmpi.b #127,d0
blo.s .1
cmpi.b #221,d0
bhi.s .10
PUTCH #MEDC
subi.b #127-32,d0
bra.s .1
.10 PUTCH #HIGHC
subi.b #222-32,d0
.1
PUTCH d0
dbra d1,.make
move.l a3,d0
move.l d7,d1
move.l d3,d2
bsr.w SAVE_FILE ;IN: d0-filename;d1-data;d2-lenght;OUT: d0=0 => O.K.
rts
ss_fail moveq #-1,d0
rts
;------------------------------------------
SaveHiScores movem.l d0-d7/a0-a6,-(sp)
bsr.w CDProggy
movea.l MyPrefs,a0
lea HsFileName,a3
movea.l MyPrefs,a4
bsr.w SaveScore
tst.l d0
bne.s save_fail
clr.b ([MyPrefs],mhs_NewHiscore)
shsc_exit
bsr.w CDBack
movem.l (sp)+,d0-d7/a0-a6
rts
save_fail lea (.sf_Text,pc),a1
lea (.sf_Button,pc),a2
bsr.w InformationReq
bra.s shsc_exit
.sf_Text dc.b 'Sorry. "Mines.hiscores" could not be saved.',0
.sf_Button dc.b 'Oh, damned!',0
cnop 0,4
;-----------------------------------------
Decrypt ;IN: a0-data, d1- length, d2-RndSeed
movem.l d0-d2/a0,-(sp)
move.l d2,RndSeed
subq.w #1,d1
.loop move.b (a0),d2
moveq #-1,d0
bsr.w Rand
add.b d0,d2
move.b d2,(a0)+
dbra d1,.loop
movem.l (sp)+,d0-d2/a0
rts
Encrypt ;IN: a0-data, d1-length, d2-RndSeed
movem.l d0-d2/a0,-(sp)
move.l d2,RndSeed
subq.w #1,d1
.loop move.b (a0),d2
moveq #-1,d0
bsr.w Rand
sub.b d0,d2
move.b d2,(a0)+
dbra d1,.loop
movem.l (sp)+,d0-d2/a0
rts
*****************************************************************
DefaultPrefs ;IN: a0-MyPrefs
movem.l d0/a0,-(sp)
move.w #prf_SIZEOF-1,d0
.clr clr.b (a0)+
dbra d0,.clr
movem.l (sp)+,d0/a0
rts
;-------------------------------------------------------------
LoadPreferences ;Loads preferences from disk to memory.
;MyPrefs == ptr to PrefsBlock
move.l MyPrefs,d0
bne.s .ready
;**alloc memory for pref. structures
move.l #prf_SIZEOF,d0
move.l #0,d1
bsr.w ADDALLOC
move.l d0,MyPrefs
beq.w noprefs.fatal
.ready
;**set preferences to default
movea.l d0,a0
bsr.w DefaultPrefs
lea (error,pc),a0
clr.b (a0)
lea (diskObj,pc),a0
clr.l (a0)
;*get tool types
movea.l (EB,PC),a6
lea (IconName,pc),a1
moveq #MinIconVer,d0
jsr (_LVOOpenLibrary,a6) ;"icon.library" V36
lea (IconBase,pc),a0
move.l d0,(a0)
beq.s noiconlib
lea ProgramName,a0
movea.l (IconBase,pc),a6
jsr (_LVOGetDiskObjectNew,a6) ;get "mines.info" or something
lea (diskObj,pc),a0
move.l d0,(a0)
beq.s noobj ;shouldn't happen...
movea.l d0,a0
movea.l (do_ToolTypes,a0),a4 ;get ToolTypes array
lea PrefItems,a3
.itloop movea.l a4,a0 ;tooltypes array
move.l (mpi_PItemName,a3),d0 ;tooltype name
beq.s .done
movea.l d0,a1
movea.l d0,a5 ;parameter for handlers
jsr (_LVOFindToolType,a6)
tst.l d0
beq.s .nextitem ;not present
;call the mpi_PItemHandler
movea.l MyPrefs,a0 ;param
movea.l d0,a1
movea.l (mpi_PItemHandler,a3),a2
movem.l a3-a6,-(sp)
jsr (a2)
movem.l (sp)+,a3-a6
.nextitem lea (mpi_SIZEOF,a3),a3
bra.s .itloop
.done
;check mprf_Custom(s)
TESTCUSTOM MACRO
tst.w (mprf_Custom\1,a0)
bne.s .ok\@
move.w (cpf_\1,a1),(mprf_Custom\1,a0)
.ok\@
ENDM
movea.l MyPrefs,a0
lea CusPFSizes,a1
TESTCUSTOM Width
TESTCUSTOM Height
TESTCUSTOM Bombs
movea.l (diskObj,pc),a0
jsr (_LVOFreeDiskObject,a6)
noobj move.l (EB,PC),a6
movea.l (IconBase,pc),a1
jsr (_LVOCloseLibrary,a6)
exitprefs
rts
;-------------------------------------------
noprefs.fatal lea noprefs_Text,a1
lea noprefs_Button,a2
bsr.w InformationReq
bra.s exitprefs
noiconlib lea (noicon_Text,pc),a1
lea (noicon_Button,pc),a2
bsr.w InformationReq
bra.s exitprefs
errBuf dc.l 0
diskObj dc.l 0
IconBase dc.l 0
IconName dc.b 'icon.library',0
noicon_Text dc.b '"icon.library" V36+ required to load preferences',0
noicon_Button dc.b 'Continue',0
error dc.b 0
even
;****Some small subroutines-------------------------------
uppercaseD0 cmpi.b #'a',d0
blo.s .noup
cmpi.b #'z',d0
bhi.s .noup
subi.b #'a'-'A',d0
.noup rts
;*******Preference items handlers**************************************
;They're called with MyPrefs pointer in A0
;A1 contains address of next char to read (the parameter)
;a4-tooltypes array, a5-tooltype name, a6-IconBase
;---------------------------------------------
Pref_PubScreen move.l a1,a3
moveq #0,d0
.count tst.b (a1)+
beq.s .end
addq.w #1,d0
bra.s .count
.end tst.l d0 ;no name after PUBSCREEN
beq.s .skip0
addq.w #1,d0
moveq #MEMF_PUBLIC,d1
bsr.w ADDALLOC
.skip0 movea.l a3,a1
move.l d0,(mprf_PubNameAdr,a0)
beq.s .skip
movea.l d0,a2
.cp move.b (a1)+,(a2)+
bne.s .cp
.skip
rts
;---------------------------------------------
Pref_ModeID movea.l a1,a2 ;store
bsr.w NumConvert
tst.l d1
bne.w errNum
move.l d0,(mprf_ModeID,a0)
rts
;---------------------------------------------
Pref_SizeX movea.l a1,a2 ;store
bsr.w NumConvert
tst.l d1
bne.w errNum
move.l #NUMF_WORD!NUMF_PLUS!NUMF_NONZERO,d1
bsr.w CheckNum
tst.l d1
bne.w errVal
move.w d0,(mprf_ScrWidth,a0)
rts
;---------------------------------------------
Pref_SizeY movea.l a1,a2 ;store
bsr.w NumConvert
tst.l d1
bne.w errNum
move.l #NUMF_WORD!NUMF_PLUS!NUMF_NONZERO,d1
bsr.w CheckNum
tst.l d1
bne.w errVal
move.w d0,(mprf_ScrHeight,a0)
rts
;---------------------------------------------
Pref_CustomScreen
move.b #TRUE,(mprf_CustomScreen,a0)
rts
;---------------------------------------------
Pref_WBLike move.b #TRUE,(mprf_WBLike,a0)
rts
;---------------------------------------------
Pref_NotCenter move.b #TRUE,(mprf_CenterWindow,a0) ;CenterWindow=no
rts
;---------------------------------------------
Pref_NotActiv move.b #TRUE,(mprf_WActivate,a0)
rts
;---------------------------------------------
Pref_NoQuest move.b #TRUE,(mprf_Question,a0)
rts
;---------------------------------------------
Pref_DeadQ move.b #TRUE,(mprf_DeadQ,a0)
rts
;---------------------------------------------
Pref_NoRMouse move.b #TRUE,(mprf_RMouseGame,a0)
rts
;---------------------------------------------------------
Pref_Warn move.b #TRUE,(mprf_Warn,a0) ;TRUE=DONOTWARN
rts
;---------------------------------------------
Pref_CountD move.b #TRUE,(mprf_CountDown,a0)
rts
;---------------------------------------------
Pref_Scale move.b #TRUE,(mprf_ScaleGfx,a0)
rts
;---------------------------------------------
Pref_WinX movea.l a1,a2 ;store
bsr.w NumConvert
tst.l d1
bne.w errNum
move.l #NUMF_WORD,d1 ;check the number type
bsr.w CheckNum
tst.l d1
bne.w errVal
move.w d0,(mprf_WinX,a0)
rts
;---------------------------------------------
Pref_WinY movea.l a1,a2 ;store
bsr.w NumConvert
tst.l d1
bne.w errNum
move.l #NUMF_WORD,d1
bsr.w CheckNum
tst.l d1
bne.w errVal
move.w d0,(mprf_WinY,a0)
rts
;---------------------------------------------
Pref_ZoomX movea.l a1,a2
bsr.w NumConvert
tst.l d1
bne.w errNum
move.l #NUMF_WORD,d1
bsr.w CheckNum
tst.l d1
bne.w errVal
move.w d0,(mprf_ZoomLeft,a0)
move.w d0,ZoomParams
rts
;---------------------------------------------
Pref_ZoomY movea.l a1,a2
bsr.w NumConvert
tst.l d1
bne.w errNum
move.l #NUMF_WORD,d1
bsr.w CheckNum
tst.l d1
bne.w errVal
move.w d0,(mprf_ZoomTop,a0)
move.w d0,ZoomParams+2
rts
;---------------------------------------------
;**Set level
CHECKLEV MACRO
movea.l a2,a0 ;tooltype value
lea (tt\1,pc),a1
jsr (_LVOMatchToolValue,a6)
tst.l d0
beq.s .no\@
movea.l (sp)+,a0
move.b #L\1,(mprf_Level,a0)
bra.s .exit
.no\@
ENDM
Pref_Level move.l a0,-(sp)
movea.l a1,a2 ;store
CHECKLEV EASY
CHECKLEV MEDIUM
CHECKLEV HARD
CHECKLEV PROFI
CHECKLEV CUSTOM
lea (errlev_Text,pc),a1
bsr.w ToolTypesError
addq.l #4,sp
.exit rts
ttEASY dc.b 'EASY',0
ttMEDIUM dc.b 'MEDIUM',0
ttHARD dc.b 'HARD',0
ttPROFI dc.b 'PROFI',0
ttCUSTOM dc.b 'CUSTOM',0
errlev_Text dc.b 'Unknown level definition.',10
dc.b 'Medium level used.',0
cnop 0,4
;---------------------------------------------
Pref_CusWid movea.l a1,a2 ;store
bsr.w NumConvert
tst.l d1
bne.w errNum
move.l #NUMF_WORD!NUMF_NONZERO!NUMF_PLUS,d1
bsr.w CheckNum
tst.l d1
bne.w errVal
move.w d0,CusPFSizes+cpf_Width
move.w d0,(mprf_CustomWidth,a0)
rts
;---------------------------------------------
Pref_CusHei movea.l a1,a2 ;store
bsr.w NumConvert
tst.l d1
bne.w errNum
move.l #NUMF_WORD!NUMF_NONZERO!NUMF_PLUS,d1
bsr.w CheckNum
tst.l d1
bne.w errVal
move.w d0,CusPFSizes+cpf_Height
move.w d0,(mprf_CustomHeight,a0)
rts
;---------------------------------------------
Pref_CusBom movea.l a1,a2 ;store
bsr.w NumConvert
tst.l d1
bne.w errNum
move.l #NUMF_WORD!NUMF_NONZERO!NUMF_PLUS,d1
bsr.w CheckNum
tst.l d1
bne.w errVal
move.w d0,CusPFSizes+cpf_Bombs
move.w d0,(mprf_CustomBombs,a0)
rts
;---------------------------------------------
Pref_Font
;**check if font=DEFAULT
movem.l a0/a1,-(sp) ;store
movea.l a1,a0 ;returned by FindToolType
lea (defaultText,pc),a1
jsr (_LVOMatchToolValue,a6)
movem.l (sp)+,a0/a1
tst.l d0
bne.s .default
;**copy font name to a buffer
lea MyFontName,a2 ;buffer (30 chars)
move.l a2,d0
moveq #30-1,d1 ;max 30 chars
.loop move.b (a1)+,(a2)+ ;copy font name
dbeq d1,.loop
tst.b MyFontName ;no name specified in tool types
beq.w .exit
move.l d0,(mprf_FontName,a0)
.exit rts
.default clr.l (mprf_FontName,a0)
rts
defaultText dc.b 'DEFAULT',0
cnop 0,4
;---------------------------------------------
Pref_FontSize
movea.l a1,a2 ;store
;**check if Fontsize=DESIGNED
movem.l a0/a1,-(sp) ;store
movea.l a1,a0 ;returned by FindToolType
lea (designedText,pc),a1
jsr (_LVOMatchToolValue,a6)
movem.l (sp)+,a0/a1 ;restore
tst.l d0
bne.s .designed
bsr.w NumConvert
tst.l d1
bne.w errNum
move.l #NUMF_WORD!NUMF_NONZERO!NUMF_PLUS,d1
bsr.w CheckNum
tst.l d1
bne.w errVal
move.w d0,(mprf_FontSize,a0)
rts
.designed clr.w (mprf_FontSize,a0) ;font size of zero means DESIGNED
rts
designedText dc.b 'DESIGNED',0
cnop 0,4
;---------------------------------------------
Pref_Iconify ;check for ICON,MENU
movea.l a1,a2
movea.l a0,a3
movea.l a2,a0
lea (iconIcon,pc),a1
jsr (_LVOMatchToolValue,a6)
tst.l d0
bne.s .icon
movea.l a2,a0
lea (iconMenu,pc),a1
jsr (_LVOMatchToolValue,a6)
tst.l d0
bne.s .menu
lea (badicon_Text,pc),a1
bsr.w ToolTypesError
.icon move.b #ICON_ICON,(mprf_Iconify,a3)
rts
.menu move.b #ICON_MENU,(mprf_Iconify,a3)
rts
badicon_Text dc.b 'Only MENU or ICON allowed.',10
dc.b 'Now ICON used.',0
iconMenu dc.b 'MENU',0
iconIcon dc.b 'ICON',0
cnop 0,4
;---------------------------------------------
Pref_GfxType
;check for STANDARD/MagicWB
movea.l a1,a2
movea.l a0,a3
movea.l a2,a0
lea (gfxStandard,pc),a1
jsr (_LVOMatchToolValue,a6)
tst.l d0
bne.s .stdgfx
movea.l a2,a0
lea (gfxMagicWB,pc),a1
jsr (_LVOMatchToolValue,a6)
tst.l d0
bne.s .magwbgfx
lea (badgfx_Text,pc),a1
bsr.w ToolTypesError
.stdgfx move.b #GFX_STANDARD,(mprf_GfxType,a3)
rts
.magwbgfx move.b #GFX_MAGICWB,(mprf_GfxType,a3)
rts
gfxStandard dc.b 'STANDARD',0
gfxMagicWB dc.b 'MAGICWB',0
badgfx_Text dc.b 'Type of requested gfx not supported.',10
dc.b 'Standard gfx used.',0
cnop 0,4
;---------------------------------------------
Pref_Palette
;check for STANDARD/MAGICWB/WBLIKE
movea.l a1,a2
movea.l a2,a0
lea (ptStandard,pc),a1
jsr (_LVOMatchToolValue,a6)
tst.l d0
bne.w Pref_PaletteStd
movea.l a2,a0
lea (ptMagicWB,pc),a1
jsr (_LVOMatchToolValue,a6)
tst.l d0
bne.w Pref_PaletteMag
movea.l a2,a0
lea (ptWBLike,pc),a1
jsr (_LVOMatchToolValue,a6)
tst.l d0
bne.w Pref_PaletteWB
;else colortable defined palette
move.b #PAL_COLORTABLE,([MyPrefs],mprf_PaletteType)
movea.l a2,a1
lea ScreenPalette+4,a3 ;skip first 2 words
moveq #PALENTRIES-1,d6
.go bsr.w NumConvert ;convert next palette entry
tst.l d1
bne.s errPalette
move.l #NUMF_LONG!NUMF_PLUS,d1
bsr.w CheckNum
tst.l d1
bne.s errPalette
;convert to LoadRGB32 format
EXTANDSAVE MACRO
bfins d1,d1{16:8}
bfins d1,d1{8:8}
bfins d1,d1{0:8}
move.l d1,(a3)+ ;save entry
ENDM
bfextu d0{8:8},d1 ;RED
EXTANDSAVE
bfextu d0{16:8},d1 ;GREEN
EXTANDSAVE
bfextu d0{24:8},d1 ;BLUE
EXTANDSAVE
.seek move.b (a1)+,d0 ;seek to next entry (",")
beq.s .ready ;zero=eol
cmpi.b #',',d0
bne.s .seek
dbra d6,.go
.ready
rts
errPalette
lea (errpal_Text,pc),a1
lea (errpal_Button,pc),a2
bsr.w InformationReq
;no rts!
;----------
Pref_PaletteStd move.b #PAL_STANDARD,([MyPrefs],mprf_PaletteType)
lea DefaultPalette,a2 ;copy once again
CopyPalette lea ScreenPalette,a3
moveq #PALENTRIES*3+2-1,d0
.loop move.l (a2)+,(a3)+
dbra d0,.loop
rts
;----------
Pref_PaletteMag move.b #PAL_MAGICWB,([MyPrefs],mprf_PaletteType)
lea MagicPalette,a2
bra.s CopyPalette
;----------
Pref_PaletteWB move.b #PAL_WBLIKE,([MyPrefs],mprf_PaletteType)
movea.l IntuiBase,a6
lea wbName,a0
jsr (_LVOLockPubScreen,a6) ;lock Workbench
lea (lockedWB,pc),a0
move.l d0,(a0)
beq.s Pref_PaletteStd ;couldn't lock WB
movea.l d0,a0
movea.l (sc_ViewPort+vp_ColorMap,a0),a0 ;cm
moveq #0,d0 ;first colors
moveq #PALENTRIES,d1 ;n-colors
lea ScreenPalette+4,a1 ;table
movea.l _GfxBase,a6
jsr (_LVOGetRGB32,a6)
movea.l IntuiBase,a6
suba.l a0,a0
movea.l (lockedWB,pc),a1
jsr (_LVOUnlockPubScreen,a6) ;unlock WB
rts
lockedWB dc.l 0
ptStream dc.l 0,0
ptStandard dc.b 'STANDARD',0
ptMagicWB dc.b 'MAGICWB',0
ptWBLike dc.b 'WBLIKE',0
errpal_Text dc.b 'Error in palette definition.',10
dc.b '(See Tool Types)',10
dc.b 'Standard palette used.',0
errpal_Button dc.b 'I',39,'ll have a look.',0
cnop 0,4
;---------------------------------------------------------
errNum ;number expected
;IN:a5-tooltype name a2-tooltype value
lea (noval_Text,pc),a1
bsr.w ToolTypesError
rts
errVal ;invalid value found
;IN:a5-tool type name a2-tooltype val.
lea (badval_Text,pc),a1
bsr.w ToolTypesError
rts
noval_Text dc.b 'Number expected.',0
badval_Text dc.b 'Invalid value defined.',0
cnop 0,4
;----------------------------------------------------------------
ToolTypesError ;IN:a1-explain text a5-tooltype name a2-tooltype param.
movem.l d1-d7/a0-a6,-(sp)
lea (tte_argarray,pc),a4
move.l a5,(a4)
move.l a2,(4,a4)
move.l a1,(8,a4)
lea (tte_Text,pc),a1
lea (tte_Button,pc),a2
movea.l _ReqToolsBase,a6
suba.l a3,a3
lea IReqTags,a0
jsr (_LVOrtEZRequestA,a6)
movem.l (sp)+,d1-d7/a0-a6
rts
tte_argarray dc.l 0,0,0
tte_Text dc.b 'Error in Tool Types.',10
dc.b '"%s=%s"',10,'%s',0
tte_Button dc.b 'I',39,'ll have a look.',0
cnop 0,4
;----------------------------------------------------------------
CheckNum ;checkes the LONG number in d0 if it matches
;the flags in d1
;RESULTS: d1.l=0 => O.K. else error
;NUMF_BYTE = 1 ;not implemented
NUMF_LONG = 0 ;this is default
NUMF_WORD = 1<<2
NUMF_NONZERO = 1<<6 ;values != 0
NUMF_PLUS = 1<<7 ;values >= 0
NUMF_MINUS = 1<<8 ;<0
move.l d1,d2
andi.l #NUMF_WORD,d2
beq.s .next
move.w d0,d3 ;do not touch d0
ext.l d3
cmp.l d0,d3
bne.s cn_NotMatch
move.l d1,d2
andi.l #NUMF_NONZERO,d2 ;test for non zero?
beq.s .nextw2 ;no
tst.l d0
beq.s cn_NotMatch
.nextw2 move.l d1,d2
andi.l #NUMF_PLUS,d2
beq.s .nextw3
tst.w d0
bmi.s cn_NotMatch
.nextw3 move.l d1,d2
andi.l #NUMF_MINUS,d2
beq.s .Matched
tst.w d0
bpl.s cn_NotMatch
bra.s .Matched
;next is for LONG
.next move.l d1,d2
andi.l #NUMF_NONZERO,d2 ;test for non zero?
beq.s .next2 ;no
tst.l d0
beq.s cn_NotMatch
.next2 move.l d1,d2
andi.l #NUMF_PLUS,d2
beq.s .next3
tst.l d0
bmi.s cn_NotMatch
.next3 move.l d1,d2
andi.l #NUMF_MINUS,d2
beq.s .Matched
tst.l d0
bpl.s cn_NotMatch
.Matched
moveq #0,d1 ;matched
rts
cn_NotMatch moveq #-1,d1
rts
;***********************************************************
NumConvert ;in a1-pointer to an ASCII number terminated by zero byte
;or by a ","
;examples: -246, 3467, 0xfc3A, $D34e, -&H1, &h23F
;Octal and binar numbers are not handled
;results in d0.l, if d1.l=0 then succes else error
move.l a2,-(sp) ;store
;**find out sign
clr.b Sign ;plus
cmpi.b #'-',(a1)
bne.s .plus
st Sign
bra.s .skip
.plus cmpi.b #'+',(a1)
bne.s mpok
.skip addq.w #1,a1 ;skip sign
mpok
;**find out about the type (DEC/HEX available at the moment...)
movea.l a1,a2 ;seek to end and uppercase
.loop move.b (a2),d0
bsr.w uppercaseD0
move.b d0,(a2)+
cmpi.b #',',d0
beq.s .1
tst.b d0
bne.s .loop
.1 subq.w #1,a2 ;points to the end byte
cmpa.l a1,a2
beq.w nc_invalid ;just no number there
move.b (a1),d1
move.w (a1),d2
cmpi.b #'$',d1
beq.s nc_hex1
cmpi.w #'&H',d2
beq.s nc_hex2
cmpi.w #'0X',d2
beq.s nc_hex2
;else decimal
nc_dec moveq #1,d2 ;10^0 .. 10^1 .. 10^2 ..
moveq #0,d0 ;result
.decLoop move.b -(a2),d1
cmpi.b #'0',d1 ;is the char in range 0-9
blo.s nc_invalid ;no
cmpi.b #'9',d1
bhi.s nc_invalid ;no
subi.b #'0',d1
extb d1
mulu.l d2,d1 ;d1:=d1*10^x
add.l d1,d0
bvs.s nc_invalid ;overflow?
mulu.l #10,d2
bvs.s nc_invalid
cmpa.l a2,a1
bne.s .decLoop
moveq #0,d1 ;succes
bra.s SignTest
nc_hex2 addq.w #1,a1 ;skip '&H' '0X'
nc_hex1 addq.w #1,a1 ;skip '$'
moveq #0,d0
moveq #31-3,d2
.hexLoop move.b -(a2),d1
cmpi.b #'0',d1 ;test range (0..9)
blo.s nc_invalid
cmpi.b #'9',d1
bls.s .ok
cmpi.b #'A',d1 ;test (A..F)
blo.s nc_invalid
cmpi.b #'F',d1
bhi.s nc_invalid
subi.b #'A'-'9'-1,d1
.ok subi.b #'0',d1
bfins d1,d0{d2:4}
cmpa.l a1,a2
beq.s nc_HexReady
subq.w #4,d2 ;next nibble
bpl.s .hexLoop ;exit if out of longword
nc_HexReady moveq #0,d1 ;succes
SignTest tst.b Sign
beq.s .ok
neg.l d0
.ok movea.l (sp)+,a2
rts
nc_invalid moveq #-1,d1 ;error
moveq #0,d0
movea.l (sp)+,a2
rts
;*****************************************************************
GetScreenCenter ;gets center of the visible part of screen
movea.l MyScreen,a5
;get screen and window sizes
movea.l (sc_ViewPort+vp_ColorMap,a5),a4
movea.l (cm_vpe,a4),a4 ;ViewPortExtra
;Winx=(ScrWidth-WinWidth)/2
move.w (vpe_DisplayClip+ra_MaxX,a4),d1
sub.w (vpe_DisplayClip+ra_MinX,a4),d1
move.w (sc_Width,a5),d0
cmp.w d0,d1 ;if screen width < display clip
bls.s .dc1
move.w d0,d1
.dc1 asr.w #1,d1 ;/2
sub.w (sc_ViewPort+vp_DxOffset,a5),d1 ;offset
move.w d1,CenterPointX
;WinY=(ScrHeight-WinHeight)/2
move.w (vpe_DisplayClip+ra_MaxY,a4),d1
sub.w (vpe_DisplayClip+ra_MinY,a4),d1
move.w (sc_Height,a5),d0
cmp.w d0,d1
bls.s .dc2
move.w d0,d1
.dc2 asr.w #1,d1 ;/2
sub.w (sc_ViewPort+vp_DyOffset,a5),d1
move.w d1,CenterPointY
rts
;*****************************************************************
SetWinParams ;sets the required window size and placement
;**Get the PlayField size
.prefs movea.l MyPrefs,a0
move.b (mprf_Level,a0),d0
bne.s .cont
move.b #LMEDIUM,d0
move.b d0,(mprf_Level,a0)
.cont lea DefPFSizes,a0
ext.w d0
move.w (a0,d0.w*8),PFWidth
move.w (2,a0,d0.w*8),PFHeight
move.w (4,a0,d0.w*8),PFBombs
clr.b d5
;check for minimal height
cmpi.w #MINPFHEIGHT,PFHeight
bhs.s .cw
move.w #MINPFHEIGHT,PFHeight
move.w #MINPFHEIGHT,(2,a0,d0.w*8)
move.w #MINPFHEIGHT,([MyPrefs],mprf_CustomHeight)
move.w d0,-(sp) ;store
lea toosmall_Text,a1
lea toosmall_Button,a2
bsr.w InformationReq
move.w (sp)+,d0
st d5 ;set flag
;check for minimal width
.cw move.w MinRowBut,d1
cmp.w PFWidth,d1
bls.s .well
move.w d1,(a0,d0.w*8)
move.w d1,([MyPrefs],mprf_CustomWidth)
move.w d1,PFWidth
tst.b d5
bne.s .well ;don't bother with messages anymore
move.w d0,-(sp) ;store
lea toosmall_Text,a1
lea toosmall_Button,a2
bsr.w InformationReq
move.w (sp)+,d0
.well
move.w PFWidth,d1 ;check for maximum mines
mulu.w PFHeight,d1
subq.w #1,d1
cmp.w PFBombs,d1
bhs.s .tmok
move.w d1,(4,a0,d0.w*8)
move.w d1,([MyPrefs],mprf_CustomBombs)
move.w d1,PFBombs
lea toomuch_Text,a1
lea toomuch_Button,a2
bsr.w InformationReq
.tmok
addq.w #2,PFWidth
addq.w #2,PFHeight
;**Set window size
move.w ButtHeight,d0 ;my bar size
add.w d0,d0
move.w d0,MyBarHeight
move.w PFWidth,d0 ;Inner sizes
subq.w #2,d0
mulu.w ButtWidth,d0
move.w d0,InnWidth
move.w PFHeight,d0
subq.w #2,d0
mulu.w ButtHeight,d0
add.w MyBarHeight,d0
move.w d0,InnHeight
setWsize movea.l MyScreen,a0
moveq #0,d2
move.w d2,d3
move.w d2,d4
move.w d2,d5
move.b (sc_WBorLeft,a0),d2
move.b (sc_WBorRight,a0),d3
move.b (sc_WBorTop,a0),d4
add.w ([sc_Font,a0],ta_YSize),d4
addq.w #1,d4
move.w d4,winBarH
move.b (sc_WBorBottom,a0),d5
move.w InnWidth,d0 ;width
add.w d2,d0 ;BorderLeft
add.w d3,d0 ; Right
move.w d0,WinWidth
move.w InnHeight,d0 ;height
add.w d4,d0 ;BorderTop
add.w d5,d0 ; Bottom
move.w d0,WinHeight
move.w d2,MinX
move.w d2,MinPFX ;(for future?)
move.w d4,MinY
add.w MyBarHeight,d4
move.w d4,MinPFY
;**Check if window is bigger than screen
movea.l MyScreen,a5
move.w WinWidth,d0
cmp.w (sc_Width,a5),d0 ;d0<=sc_Width?
bls.s .skip
move.w (sc_Width,a5),WinWidth ;validate
st Disable
st DisplayTooBig ;inform the user
; set new InnWidth
movea.l MyScreen,a0
move.b (sc_WBorLeft,a0),d0
add.b (sc_WBorRight,a0),d0
ext.w d0
sub.w WinWidth,d0
neg.w d0
move.w d0,InnWidth
.skip move.w WinHeight,d0
cmp.w (sc_Height,a5),d0 ;d0<=sc_Height?
bls.s .skip2
move.w (sc_Height,a5),WinHeight
st Disable
st DisplayTooBig ;inform the user
; set new InnHeight
movea.l MyScreen,a0
move.b (sc_WBorBottom,a0),d0
ext.w d0
add.w winBarH,d0
sub.w WinHeight,d0
neg.w d0
move.w d0,InnHeight
.skip2
;**Set placement for the window
movea.l MyPrefs,a0
; Get type of placement from prefs
tst.b (mprf_CenterWindow,a0)
beq.s InTheCenter ;default
; 1. Abs position
tst.b CPointSet
bne.s InTheCenter
st CPointSet
move.w (mprf_WinX,a0),d0 ;set new center point
move.w d0,WinX
move.w WinWidth,d1
asr.w #1,d1
add.w d1,d0
move.w d0,CenterPointX
move.w (mprf_WinY,a0),d0
move.w d0,WinY
move.w WinHeight,d1
asr.w #1,d1
add.w d1,d0
move.w d0,CenterPointY
bra.s itc_skip
; 2. in the center of default screen
InTheCenter move.w WinWidth,d1
asr.w #1,d1 ;/2
sub.w CenterPointX,d1
neg.w d1
move.w d1,WinX
move.w WinHeight,d1
asr.w #1,d1
sub.w CenterPointY,d1
neg.w d1
move.w d1,WinY
itc_skip
move.w PFWidth,d0
subq.w #2,d0
mulu.w ButtWidth,d0
move.w d0,PFXPix
move.w PFHeight,d0
subq.w #2,d0
mulu.w ButtHeight,d0
move.w d0,PFYPix
rts
;-----------------------------------------------------------
SetZoomParams
;set zoom parameters
move.w DefPFSizes+(LEASY*8),d0 ;PFWidth for EASY level
mulu.w ButtWidth,d0
move.b ([MyScreen],sc_WBorLeft),d1
add.b ([MyScreen],sc_WBorRight),d1
ext.w d1
add.w d1,d0
lea ZoomParams,a0
tst.w (a0) ;ZoomLeft already set by LoadPreferences?
bpl.s .yes1
move.w WinX,(a0) ;left
move.w WinX,([MyPrefs],mprf_ZoomLeft)
.yes1 tst.w (2,a0) ;ZoomTop already set by LoadPreferences?
bpl.s .yes2
move.w WinY,(2,a0) ;top
move.w WinY,([MyPrefs],mprf_ZoomTop)
.yes2 move.w d0,(4,a0) ;width
move.w winBarH,(6,a0) ;height
move.w d0,ZoomWidth
move.w winBarH,ZoomHeight
rts
;-----------------------------------------------------------
SetWinTagList ;Set values got from SetWinParams to MyWinTags
lea MyWinTags,a0
SetTagsLoop move.l (a0)+,d0
beq.s .done ;TAG_DONE
cmpi.l #WA_InnerWidth,d0
beq.s .innwidth
cmpi.l #WA_InnerHeight,d0
beq.s .innheight
cmpi.l #WA_Left,d0 ;set WinX?
beq.s .left
cmpi.l #WA_Top,d0 ;set WinY?
beq.s .top
cmpi.l #WA_Activate,d0
beq.s .activate
cmpi.l #WA_CustomScreen,d0
beq.s .custom
cmpi.l #WA_PubScreenName,d0
beq.s .pubscreen
.nexttag addq.w #4,a0 ;skip ti_Data
bra.s SetTagsLoop
.done rts ;SetWinTags EXIT
.innwidth move.w InnWidth,(2,a0)
bra.s .nexttag
.innheight move.w InnHeight,(2,a0)
bra.s .nexttag
.left move.w WinX,(2,a0)
bra.s .nexttag
.top move.w WinY,(2,a0)
bra.s .nexttag
.activate move.b ([MyPrefs],mprf_WActivate),d0
not.b d0 ;inversed logic
extb d0
move.l d0,(a0) ;WA_Activate flag
bra.s .nexttag
.custom move.l MyScreen,(a0)
tst.b ([MyPrefs],mprf_CustomScreen)
bne.s .nexttag
move.l #TAG_IGNORE,(-4,a0)
bra.s .nexttag
.pubscreen move.l ([MyPrefs],mprf_PubNameAdr),(a0)
bra.s .nexttag
;*************************************************************************
;*********LOAD FILE************
LOAD_FILE ;IN: d0-filename
;OUT:d0-address of loaded data ERROR=0
; d1-lenght of ^
movem.l d2-d7/a0-a6,-(sp)
movea.l DosBase,a6
clr.l lf_buffer
clr.l lf_fileLen
;***get lenght of the source file
move.l d0,lf_filename
move.l lf_filename,d1 ;filename
move.l #ACCESS_READ,d2 ;acces mode
jsr (_LVOLock,a6) ;lock the file
tst.l d0
beq.w lf_nolock
move.l d0,lf_fileLock ;store pointer
move.l lf_fileLock,d1
move.l #lf_fib,d2 ;file info block
jsr (_LVOExamine,a6) ;fill the FIB structure
tst.l d0
beq.s lf_unlock
move.l lf_fib+$7c,lf_fileLen
;***Allocate memory buffer
move.l lf_fileLen,d0 ;file lenght=size of buffer
moveq #MEMF_PUBLIC,d1
bsr ADDALLOC
move.l d0,lf_buffer
beq.s lf_no_mem
;***open file to be loaded
move.l lf_filename,d1 ;source filename
move.l #MODE_OLDFILE,d2 ;acces mode
jsr (_LVOOpen,a6) ;open file
move.l d0,lf_fhandle
beq.s lf_erroropen
;***load file to buffer
move.l lf_fhandle,d1 ;file
move.l lf_buffer,d2
move.l lf_fileLen,d3
jsr (_LVORead,a6) ;read from file
cmp.l d0,d3
bne.s lf_Error
EndOfFile ;***file loaded->close and unlock
lf_close move.l lf_fhandle,d1
jsr (_LVOClose,a6)
lf_unlock move.l lf_fileLock,d1
jsr (_LVOUnLock,a6)
lf_nolock move.l lf_buffer,d0
move.l lf_fileLen,d1
movem.l (sp)+,d2-d7/a0-a6
rts
;------------------
lf_Error clr.l lf_buffer
bra.s lf_close
lf_no_mem
lf_erroropen clr.l lf_buffer
bra.s lf_unlock
;**************SAVE FILE*******************************************************
SAVE_FILE ;IN: d0-filename
; d1-data
; d2-lenght
;OUT: d0=0 => O.K.
movem.l d1-d7/a0-a6,-(sp)
movea.l DosBase,a6
move.l d0,lf_filename
move.l d1,d4 ;store
move.l d2,d5
;***Open file
move.l lf_filename,d1
move.l #MODE_NEWFILE,d2
jsr (_LVOOpen,a6) ;open file
move.l d0,lf_fhandle
beq.s sf_erroropen
;***write buffer
move.l lf_fhandle,d1 ;fhandle
move.l d4,d2 ;buffer
move.l d5,d3 ;lenght
jsr (_LVOWrite,a6)
cmp.l d0,d3
bne.s sf_errorwrite
;***saved->close file
clr.l -(sp)
sf_close move.l lf_fhandle,d1
jsr (_LVOClose,a6)
sf_exit
move.l (sp)+,d0
movem.l (sp)+,d1-d7/a0-a6
rts
sf_erroropen move.l #-1,-(sp)
bra.s sf_exit
sf_errorwrite move.l #-1,-(sp)
bra.s sf_close
;*****************************************************************
ADDALLOC ;IN - d0-size,d1-flags
movem.l a0/a1/a6,-(sp)
movea.l (EB,PC),a6
move.l d0,-(sp) ;store size
jsr (_LVOAllocMem,a6)
movea.l AllocPos,a0
move.l d0,(a0)+ ;addr
beq.s .nomem
addq.l #8,AllocPos
.nomem move.l (sp)+,(a0) ;size
movem.l (sp)+,a0/a1/a6
rts
;*****************************************************************
;********FreeAllMemory ;..also if nothing was allocated.
FreeAllMemory move.l (EB,PC),a6
lea Allocated,a5
FM_Loop move.l (a5)+,d0 ;Get addr
beq.s FM_Done ;End of structure?
movea.l d0,a1
move.l (a5)+,d0 ;Get size
jsr (_LVOFreeMem,a6) ;Free block
bra.s FM_Loop
FM_Done rts
;*****************************************************************
FreeMemBlock ;IN: a1-address
;Searches in the "Allocated" structure
;for matching values and frees memory
movem.l d0/d1/a0/a6,-(sp)
lea Allocated,a0
fmb_next move.l (a0)+,d1
beq.s fmb_NotFound
move.l (a0)+,d0 ;size
cmpa.l d1,a1 ;check address
bne.s fmb_next
;found. Free it now.
move.l a0,-(sp) ;store structure position
movea.l (EB,PC),a6
jsr (_LVOFreeMem,a6)
;cut item from the structure
movea.l (sp)+,a0
movea.l a0,a1
subq.l #8,a0 ;free block
.loop move.l (a1)+,(a0)+
beq.s .ok
move.l (a1)+,(a0)+
bra.s .loop
.ok subq.l #8,AllocPos ;structure is now shorter
fmb_NotFound movem.l (sp)+,d0/d1/a0/a6
rts
;---------------------------------------------------------------------------
InitSemaphore ;IN: NIL OUT: d0 - addr. of the structure or FALSE
;Unfortunally, when calling this routine the ADDALLOC
;system is not initialized yet, so don't forget to free
;"Semaphore" manually (call "FreeSemaphore")
movea.l (EB,PC),a6
move.l #SS_SIZE,d0 ;Signal semaphore - sizeof
move.l #MEMF_PUBLIC!MEMF_CLEAR,d1
jsr (_LVOAllocMem,a6)
move.l d0,Semaphore
beq.s .error
move.l d0,d2 ;store
movea.l (EB,PC),a6
movea.l d0,a0
jsr (_LVOInitSemaphore,a6) ;void()
move.l d2,d0 ;ret. code
.error rts
FreeSemaphore movea.l (EB,PC),a6
movea.l Semaphore,a1
move.l #SS_SIZE,d0
jsr (_LVOFreeMem,a6)
rts
;---------------------------------------------------------------------------
CallOtherSweeper
bsr.s InitSemaphore
tst.l d0
beq.s .noSemaphore
movea.l (EB,PC),a6
jsr (_LVOCreateMsgPort,a6)
tst.l d0
beq.s .exit
movea.l d0,a4 ;store
movea.l Semaphore,a0
jsr (_LVOObtainSemaphore,a6)
lea (MinesPortName,pc),a1
jsr (_LVOFindPort,a6)
tst.l d0
beq.s .nomines
movea.l d0,a3
lea (COSMsg,pc),a1 ;msg
move.l a4,(MN_REPLYPORT,a1)
move.w #am_ID+4,(MN_LENGTH,a1)
move.l #'MINE',(am_ID,a1)
movea.l a3,a0 ;port
jsr (_LVOPutMsg,a6) ;hey! wake up!
movea.l a4,a0
jsr (_LVOWaitPort,a6) ;wait for reply
addq.l #4,a7 ;rts
movea.l Semaphore,a0
jsr (_LVOReleaseSemaphore,a6)
bsr.w FreeSemaphore
bra.s .skp
.nomines
movea.l Semaphore,a0
jsr (_LVOReleaseSemaphore,a6)
.skp
movea.l a4,a0
jsr (_LVODeleteMsgPort,a6)
rts
.exit
;free Semaphore structure
bsr.w FreeSemaphore
.noSemaphore addq.l #4,a7 ;rts
rts
COSMsg dcb.b am_ID+4,0
cnop 0,4
;*****************************************************************
EB dc.l 0 ;****ExecBase
;*****************************************************************
SECTION wbstartup,CODE
_IconStart movem.l d0/a0,-(sp) ;prik. radka
sub.l a1,a1 ;a1=0 - vlastni task
movea.l 4.w,a6
jsr (_LVOFindTask,a6)
movea.l d0,a2
tst.l ($ac,a2) ;z WB? pr_CLI
bne.s From_CLI ; ne
* from WorkBench *
lea ($5c,a2),a2 ;pr_MsgPort
move.l a2,a0
jsr (_LVOWaitPort,a6)
move.l a2,a0
jsr (_LVOGetMsg,a6)
lea (WBmessage,PC),a0
move.l d0,(a0)
movem.l (sp)+,d0/a0
bra.s CoWB_run
From_CLI movem.l (sp)+,d0/a0 ;d0 = d×lka pÒÉk. ÒÁdky vÃetnÅ LF ($a)
;a0 ->na 1. znak ÒÁdky (Ucase<>Lcase)
CoWB_run jsr _main
CoWB_end move.l d0,-(sp) ;returncode
* nÁvrat do CLI | WB ? *-------------------------
tst.l (WBmessage,pc)
beq.s To_CLI
movea.l 4.w,a6
jsr (_LVOForbid,a6)
move.l (WBmessage,pc),a1
jsr (_LVOReplyMsg,a6)
To_CLI move.l (sp)+,d0 ;Errorcode
rts
WBmessage dc.l 0
SECTION GfxData,DATA_C
INCDIR "SOURCES:Mines/gfx/"
rawFlag INCBIN "Flag.raw"
rawNoFlag INCBIN "NoFlag.raw"
rawBomb INCBIN "Bomb.raw"
rawBlowed INCBIN "Blowed.raw"
rawMagicFlag INCBIN "MagicFlag.raw"
rawMagicNoFlag INCBIN "MagicNoFlag.raw"
rawMagicBomb INCBIN "MagicBomb.raw"
rawMagicBlowed INCBIN "MagicBlowed.raw"
rawSun INCBIN "Sun.raw"
rawSunPressed INCBIN "Sun.pressed.raw"
rawSunLoose INCBIN "Sun.loose.raw"
rawSunWon INCBIN "Sun.won.raw"
rawNumbers INCBIN "Numbers1bpl.raw"
SECTION MinesData,DATA
;**Bitmap structures for predefined gfx
bmapFlag dc.w ((BUTMINX-1)/16+1)*2 ;bm_BytesPerRow
dc.w BUTMINY ;bm_Rows
dc.b 0 ;bm_Flags
dc.b BUTMAXBPL ;bm_Depth
dc.w 0 ;bm_Pad
dc.l 0,0,0,0,0,0,0,0
bmapNoFlag dc.w ((BUTMINX-1)/16+1)*2 ;bm_BytesPerRow
dc.w BUTMINY ;bm_Rows
dc.b 0 ;bm_Flags
dc.b BUTMAXBPL ;bm_Depth
dc.w 0 ;bm_Pad
dc.l 0,0,0,0,0,0,0,0
bmapBomb dc.w ((BUTMINX-1)/16+1)*2 ;bm_BytesPerRow
dc.w BUTMINY ;bm_Rows
dc.b 0 ;bm_Flags
dc.b BUTMAXBPL ;bm_Depth
dc.w 0 ;bm_Pad
dc.l 0,0,0,0,0,0,0,0
bmapBlowed dc.w ((BUTMINX-1)/16+1)*2 ;bm_BytesPerRow
dc.w BUTMINY ;bm_Rows
dc.b 0 ;bm_Flags
dc.b BUTMAXBPL ;bm_Depth
dc.w 0 ;bm_Pad
dc.l 0,0,0,0,0,0,0,0
;**image structures for gadget-sun
img_Sun dc.w 0 ;ig_LeftEdge
dc.w 0 ;ig_TopEdge
dc.w SUNMINX ;ig_Width (though data is word-aligned)
dc.w SUNMINY ;ig_Height
dc.w SUNMAXBPL ;ig_Depth
dc.l rawSun ;ig_ImageData
dc.b %111,0
dc.l 0
img_SunPressed dc.w 0 ;ig_LeftEdge
dc.w 0 ;ig_TopEdge
dc.w SUNMINX ;ig_Width (though data is word-aligned)
dc.w SUNMINY ;ig_Height
dc.w SUNMAXBPL ;ig_Depth
dc.l rawSunPressed ;ig_ImageData
dc.b %111,0
dc.l 0
img_SunLoose dc.w 0 ;ig_LeftEdge
dc.w 0 ;ig_TopEdge
dc.w SUNMINX ;ig_Width (though data is word-aligned)
dc.w SUNMINY ;ig_Height
dc.w SUNMAXBPL ;ig_Depth
dc.l rawSunLoose ;ig_ImageData
dc.b %111,0
dc.l 0
img_SunWon dc.w 0 ;ig_LeftEdge
dc.w 0 ;ig_TopEdge
dc.w SUNMINX ;ig_Width (though data is word-aligned)
dc.w SUNMINY ;ig_Height
dc.w SUNMAXBPL ;ig_Depth
dc.l rawSunWon ;ig_ImageData
dc.b %111,0
dc.l 0
img_Number dc.w 0 ;ig_LeftEdge
dc.w 0 ;ig_TopEdge
dc.w NUMWIDTH ;ig_Width (though data is word-aligned)
dc.w NUMHEIGHT ;ig_Height
dc.w 2 ;ig_Depth
dc.l 0 ;ig_ImageData
dc.b %100,0 ;ig_PlanePick,ig_PlaneOnOff
dc.l 0
SunGadget dc.l 0 ;gg_NextGadget
dc.w 0 ;gg_LeftEdge
dc.w 0 ;gg_TopEdge
dc.w SUNMINX ;gg_Width
dc.w SUNMINY ;gg_Height
dc.w GFLG_GADGIMAGE!GFLG_GADGHIMAGE ;gg_Flags
dc.w GACT_RELVERIFY!GACT_IMMEDIATE ;gg_Activation
dc.w 0 ;gg_GadgetType
dc.l 0 ;gg_GadgetRender
dc.l 0 ;gg_SelectRender
dc.l 0 ;gg_GadgetText ; text for this gadget;
dc.l 0 ;gg_MutualExclude ; obsolete
dc.l 0 ;gg_SpecialInfo
dc.w 0 ;gg_GadgetID ; user-definable ID field
dc.l 0 ;gg_UserData ;(ignored by Intuit)
Gadget_Image dc.l 0
;-----------------EndGadget
;-------------------------------------------------------------------
IntuiName dc.b 'intuition.library',0
GfxName dc.b 'graphics.library',0
DosName dc.b 'dos.library',0
ReqToolsName dc.b 'reqtools.library',0
DiskFontName dc.b 'diskfont.library',0
GadtoolsName dc.b 'gadtools.library',0
UtilityName dc.b 'utility.library',0
TimDevName dc.b 'timer.device',0
wbName dc.b 'Workbench',0
;**This is the main window**********************************
cnop 0,4
MyWinTags
dc.l WA_Left,0
dc.l WA_Top,0
dc.l WA_InnerWidth,0
dc.l WA_InnerHeight,0
dc.l WA_CustomScreen,0
dc.l WA_Title,MyWinTitle
dc.l WA_ScreenTitle,MyWinScrTitle
dc.l WA_PubScreenName,0
; **some flags now
dc.l WA_Activate,FALSE ;default is false
dc.l WA_DragBar,TRUE
dc.l WA_DepthGadget,TRUE
dc.l WA_CloseGadget,TRUE
dc.l WA_Zoom,ZoomParams
dc.l WA_SmartRefresh,TRUE
dc.l WA_NewLookMenus,TRUE ;V39
dc.l WA_ReportMouse,TRUE
dc.l WA_IDCMP,0
dc.l WA_Gadgets,0
dc.l WA_RptQueue,0
dc.l WA_MouseQueue,3
dc.l TAG_DONE,0
ZoomParams dc.w -1,-1,0,0
;***O.k. That was my window***********************************
;***Now the screen
MyScreenTags
dc.l SA_Title,MyScrTitle
dc.l SA_Type,CUSTOMSCREEN
dc.l SA_MinimizeISG,TRUE ;V40
dc.l SA_AutoScroll,TRUE
dc.l SA_LikeWorkbench,0 ;V39
dc.l SA_Depth,BUTMAXBPL
dc.l SA_Left,0
dc.l SA_Top,0
dc.l SA_Width,0 ;set by OpenMyScreen
dc.l SA_Height,0
dc.l SA_Overscan,OSCAN_TEXT
dc.l SA_Pens,newLook
dc.l SA_SysFont,1 ;WB screen font
dc.l SA_DisplayID,0
dc.l TAG_DONE,0
newLook dc.w -1
PALENTRIES = 8
DefaultPalette dc.w PALENTRIES,0
dc.l $AAAAAAAA,$AAAAAAAA,$AAAAAAAA,$00000000,$00000000,$00000000
dc.l $FFFFFFFF,$FFFFFFFF,$FFFFFFFF,$66666666,$88888888,$BBBBBBBB
dc.l $EEEEEEEE,$44444444,$44444444,$55555555,$DDDDDDDD,$55555555
dc.l $00000000,$44444444,$DDDDDDDD,$EEEEEEEE,$99999999,$00000000
dc.l 0
MagicPalette dc.w PALENTRIES,0
dc.l $95959595,$95959595,$95959595,$00000000,$00000000,$00000000
dc.l $FFFFFFFF,$FFFFFFFF,$FFFFFFFF,$3B3B3B3B,$67676767,$A2A2A2A2
dc.l $7B7B7B7B,$7B7B7B7B,$7B7B7B7B,$AFAFAFAF,$AFAFAFAF,$AFAFAFAF
dc.l $AAAAAAAA,$90909090,$7C7C7C7C,$FFFFFFFF,$A9A9A9A9,$97979797
dc.l 0
MyWinTitle dc.b 'MineSweeper '
dc.b V,E,R,S,I
dc.b 0
MyScrTitle
MyWinScrTitle dc.b 'MineSweeper '
dc.b V,E,R,S,I,' PEGAS Software (May-1997)'
dc.b 0
;just version information
dc.b 0,'$VER: MineSweeper '
dc.b V,E,R,S,I
dc.b ' (21.5.97)',0
;*****Menu structures*************************
cnop 0,4
NewMenuTags dc.l GTMN_FullMenu,TRUE
dc.l TAG_DONE,0
LayoutTags dc.l GTMN_NewLookMenus,TRUE
dc.l TAG_DONE,0
MyMenu dc.b NM_TITLE,0 ;They must be in this order...
dc.w 0,0 ;MENUENABLED
dc.l 0,0,MGame,0
;**
dc.b NM_ITEM,0
dc.w $f800,STDFLAGS
dc.l csStrt,0,MStart,mh_Start
dc.b NM_ITEM,0
dc.w $f800!1<<MIS,STDFLAGS
dc.l csPaus,0,MPause,mh_Pause
dc.b NM_ITEM,0
dc.w $f800!2<<MIS,STDFLAGS
dc.l csAbou,0,MAbout,mh_About
dc.b NM_ITEM,0
dc.w $f800!3<<MIS,0
dc.l 0,0,NM_BARLABEL,0
dc.b NM_ITEM,0
dc.w $f800!4<<MIS,STDFLAGS
dc.l csIcon,0,MIcon,mh_Iconify
dc.b NM_ITEM,0
dc.w $f800!5<<MIS,STDFLAGS
dc.l csQuit,0,MQuit,mh_Quit
;***************************
dc.b NM_TITLE,0
dc.w 0,0 ;MENUENABLED
dc.l 0,0,MScores,0
dc.b NM_ITEM,0
dc.w $f801,STDFLAGS
dc.l csHisc,0,MHiScores,mh_HiScores
dc.b NM_ITEM,0
dc.w $f801!1<<MIS,STDFLAGS
dc.l 0,0,MClearHi,0
dc.b NM_SUB,0
dc.w $0001!(1<<MIS),STDFLAGS
dc.l 0,0,MClrCustom,mh_ClearCustom
dc.b NM_SUB,0
dc.w $0001!(1<<MIS)!(1<<SIS),STDFLAGS
dc.l 0,0,MClrAll,mh_ClearAll
dc.b NM_ITEM,0
dc.w $f801!2<<MIS,STDFLAGS
dc.l 0,0,MJoin,mh_JoinScores
dc.b NM_ITEM,0
dc.w $f801!3<<MIS,STDFLAGS
dc.l csSaHi,0,MSave,mh_SaveScores
;***************************
dc.b NM_TITLE,0
dc.w 0,0 ;MENUENABLED
dc.l 0,0,MLevel,0
LevelItems dc.b NM_ITEM,0
dc.w $f802,MCHECK
dc.l csLev1,$fffe,MEasy,mh_Level
dc.b NM_ITEM,0
dc.w $f802!1<<MIS,MCHECK
dc.l csLev2,$fffd,MMedium,mh_Level
dc.b NM_ITEM,0
dc.w $f802!2<<MIS,MCHECK
dc.l csLev3,$fffb,MHard,mh_Level
dc.b NM_ITEM,0
dc.w $f802!3<<MIS,MCHECK
dc.l csLev4,$fff7,MProfi,mh_Level
dc.b NM_ITEM,0
dc.w $f802!4<<MIS,MCHECK
dc.l csLev5,$ffef,MCustom,mh_Level
;***************************
dc.b NM_TITLE,0
dc.w 0,0 ;MENUENABLED
dc.l 0,0,MSettings,0
;**
dc.b NM_ITEM,0
dc.w $f803,STDFLAGS
dc.l csPref,0,MPrefs,mh_AdjustPrefs
dc.b NM_ITEM,0
dc.w $f803!1<<MIS,STDFLAGS
dc.l 0,0,MSavePrefs,mh_SavePrefs
dc.b NM_END,0
dc.l 0,0,0,0,0
MMI_NUMOF = 25 ;don't forget!! (include NM_END)
csStrt dc.b 'S'
csAbou dc.b '?'
csHisc dc.b 'H'
csSaHi dc.b 'W'
csLev1 dc.b '1'
csLev2 dc.b '2'
csLev3 dc.b '3'
csLev4 dc.b '4'
csLev5 dc.b '5'
csIcon dc.b 'I'
csQuit dc.b 'Q'
csPref dc.b 'A'
csPaus dc.b 'P'
MGame dc.b 'GAME',0
MStart dc.b 'Start',0
MPause dc.b 'Pause',0
MAbout dc.b 'About',0
MIcon dc.b 'Iconify ',0
MQuit dc.b 'QUIT',0
MScores dc.b 'Hi-Scores',0
MHiScores dc.b 'Show',0
MClearHi dc.b 'Clear ',0
MClrCustom dc.b 'Custom',0
MClrAll dc.b 'All',0
MJoin dc.b 'Join',0
MSave dc.b 'Save',0
MLevel dc.b 'Level',0
MEasy dc.b 'Easy',0
MMedium dc.b 'Medium',0
MHard dc.b 'Hard',0
MProfi dc.b 'Profi',0
MCustom dc.b 'Custom',0
MSettings dc.b 'Settings',0
MPrefs dc.b 'Adjust',0
MSavePrefs dc.b 'Save',0
;**inform. requests
nointui_Text dc.b '"intuition.library" V39 required!',0
nointui_Button dc.b 'I see.',0
nodos_Text dc.b '"dos.library" V36 required!',0
nodos_Button dc.b 'I see.',0
nogfx_Text dc.b '"graphics.library" V39 required!',0
nogfx_Button dc.b 'I see.',0
nogad_Text dc.b '"gadtools.library" V36 required!',0
nogad_Button dc.b 'I see.',0
noutility_Text dc.b '"utility.library V36 required!',0
noutility_Button dc.b 'I see.',0
noreq_Text dc.b '"reqtools.library" V38 required!',10,0 ;for PrintText
notclosed_Text dc.b 'ERROR: Couldn',39,'t close output file.',0
nomenu_Text dc.b 'Couldn',39,'t allocate menu structures.',0
nomenu_Button dc.b 'Continue',0
NoScr_Text dc.b 'Failed to open required screen.',0
NoScr_Button dc.b 'Continue',0
nowin_Text dc.b 'Failed to open required window.',0
nowin_Button dc.b 'Continue',0
nofont_Text dc.b 'Failed to open required font.',10
dc.b 'Default font is used.',0
nofont_Button dc.b 'I see.',0
noprefs_Text dc.b 'There',39,'s no memory for Preference structure.',0
noprefs_Button dc.b 'Exit',0
changed_Text dc.b 'Hey! Somebody has changed the window!!',10
dc.b '( Sorry, not me!! )',0
changed_Button dc.b 'Well...',0
nomygfx_Text dc.b 'No chip memory for gfx.',0
nomygfx_Button dc.b 'Well...',0
nopf_Text dc.b 'Fatal lack of memory.',0
nopf_Button dc.b 'Exit MineSweeper',0
pfbig_Text dc.b 'Sorry, but the required playfield is too big.',10
dc.b 'I can handle only 65535 buttons.',10
dc.b '( That',39,'s e.G. 85 x 771 or 255 x 257 :)',10,10
dc.b 'Sorry, but this is a fatal error :( ',0
pfbig_Button dc.b 'Exit MineSweeper',0
toobig_Text dc.b 'The playfield size is too big for your screen.',0
toobig_Button dc.b 'I see..',0
oldproc_Text dc.b 'Sorry, but I prefer a 68020+',0
oldproc_Button dc.b 'O.K. I',39,'ll upgrade.',0
oldks_Text dc.b 'System 3.0+ (V39+) required.',0
oldks_Button dc.b 'No money.',0
notimd_Text dc.b 'Sorry. Couldn',39,'t open "timer.device"',0
notimd_Button dc.b 'Abort',0
unexp_Text dc.b 'Couldn',39,'t open required window',10
dc.b '(perhaps low memory or something..)',0
unexp_Button dc.b 'O.K.',0
nopubport_Text dc.b 'Couldn',39,'t open message port.',0
nopubport_Button dc.b 'Leave',0
noidcmp_Text dc.b 'Couldn',39,'t open IDCMP communication port.',0
noidcmp_Button dc.b 'Exit',0
toolong_Text dc.b '(TIME OUT!)',10
dc.b 'SORRY! UNFORTUNALLY, I WAS NOT INFORMED ABOUT YOUR IQ.',10
dc.b 'BUT DO NOT PANIC. JUST MOVE THE POINTER TO THE BUTTON BELOW',10
dc.b 'THIS TEXT AND PRESS LEFT BUTTON OF THE THING, YOU ARE MOVING WITH.',10
dc.b 'THEN TRY TO FIND THE "CLOSE GADGET".',10
dc.b 'IT IS IN THE UPPER-LEFT CORNER OF THE RECTANGLE,',10
dc.b 'WHICH CONTAINS THOSE MANY SQUARES AND THE SUN. GOOD LUCK!',10
dc.b '(hope you got it..! :-)',0
toolong_Button dc.b 'HERE! PRESS HERE!!',0
toomuch_Text dc.b 'There are too many mines on custom level.',10
dc.b 'It must be max. Width*Height-1',0
toomuch_Button dc.b 'O.K. Let',39,'s correct it.',0
toosmall_Text dc.b 'The window would be too small for this button-sizes',10
dc.b 'and the specified PF width.',0
toosmall_Button dc.b 'OK Let',39,'s correct it',0
surec_Text dc.b 'Are you sure to clear custom hi-scores?',0
surec_Button dc.b 'Yes|No',0
surea_Text dc.b 'Are you sure to clear all hi-scores?',0
surea_Button dc.b 'Yes|No',0
xmas_Text dc.b ' --- PEGAS SOFTWARE WISH YOU MERRY CHRISTMAS ---',10,10
dc.b 'These are personal wishes from Andry :',10
dc.b 'Lack of depression, lot of love, many presents',10
dc.b 'and a wonderful Christmas-tree.',10
dc.b '----------------------------------------------------',10,10
dc.b 'Well, did you pay for this game?',10
dc.b 'Not yet? ... oh , you are going to!',10
dc.b 'Then it',39,'s all right.',0
xmas_Button dc.b 'Enjoy MineSweeper',0
about_Text dc.b 10,'MineSweeper '
dc.b V,E,R,S,I
dc.b 10,'-----------------',10
dc.b 'PEGAS Software (Mai-1997)',10,10
dc.b ' Code: Andry e-mail: xbednar@fi.muni.cz',10
dc.b ' tel: +420-641-68284',10,10
dc.b ' Gfx : Troda e-mail: kozubv@vtx.cz',10
dc.b ' tel: +420-641-204595',10,10,10
dc.b ' Language: 100%% assembler',10
dc.b 'Compiled with: PhxAss v4.35(alpha) (freeware!!!)',10
dc.b ' by Frank Wille. (Danke sehr :)',10,10
dc.b 'This program is freeware, but a little support',10
dc.b 'would be nice :) ...refer to documentation.',10
dc.b 0
about_Button dc.b 'Enjoy!',0
HiScoresButton dc.b 'Hmmm...',0
HiScoresButtonSave dc.b 'Save|Don',39,'t save',0
HsFileName dc.b 'Mines.hiscores',0
cnop 0,4
AboutTags
HiScoresTags dc.l RT_Window,0
dc.l RT_TextAttr,MyTextAttr
dc.l TAG_DONE,0
IReqTags dc.l RTEZ_Flags,EZREQF_CENTERTEXT
dc.l RT_Window,0
dc.l TAG_DONE,0
JoinGetTags dc.l RT_Window,0
dc.l RTFI_Flags,FREQF_MULTISELECT!FREQF_PATGAD
dc.l RTFI_OkText,join_Text
dc.l TAG_DONE,0
GSReqTags dc.l RT_Window,0
dc.l RTGS_Flags,GSREQF_CENTERTEXT
dc.l RTGS_TextFmt,hsgs_text
dc.l TAG_DONE,0
hsgs_text dc.b 'You have reached the high score.',10
dc.b 'Please enter your name.',0
cnop 0,4
;**For bevel boxes
VisualInfo dc.l 0
dbb_TagList1 dc.l GT_VisualInfo,0 ;normal button
dc.l GTBB_FrameType,BBFT_BUTTON
dc.l TAG_DONE,0
dbb_TagList2 dc.l GT_VisualInfo,0 ;recessed button
dc.l GTBB_FrameType,BBFT_BUTTON
dc.l GTBB_Recessed,TRUE
dc.l TAG_DONE,0
MyTextAttr dcb.b ta_SIZEOF,0
cnop 0,4
pnrt_Text dc.l 0 ;ptr to the final text
pnrt_Button dc.b 'I',39,'ll have a look',0
cnop 0,4
PrefItems
dc.l PNameCustom,Pref_CustomScreen,sp_CustomScreen
dc.l PNamePub,Pref_PubScreen,sp_PubScreen
dc.l PNameLevel,Pref_Level,sp_Level
dc.l PNameCusWid,Pref_CusWid,sp_CusWid
dc.l PNameCusHei,Pref_CusHei,sp_CusHei
dc.l PNameCusBom,Pref_CusBom,sp_CusBom
dc.l PNameWBLike,Pref_WBLike,sp_WBLike
dc.l PNameNotCenter,Pref_NotCenter,sp_NotCenter
dc.l PNameNotActivate,Pref_NotActiv,sp_NotActiv
dc.l PNameNoQuestion,Pref_NoQuest,sp_NoQuest
dc.l PNameDeadQ,Pref_DeadQ,sp_DeadQ
dc.l PNameCountD,Pref_CountD,sp_CountD
dc.l PNameNoRMouse,Pref_NoRMouse,sp_NoRMouse
dc.l PNameWarn,Pref_Warn,sp_Warn
dc.l PNameScale,Pref_Scale,sp_Scale
dc.l PNamePalette,Pref_Palette,sp_Palette
dc.l PNameGfx,Pref_GfxType,sp_GfxType
dc.l PNameIconify,Pref_Iconify,sp_Iconify
dc.l PNameModeID,Pref_ModeID,sp_ModeID
dc.l PNameSizeX,Pref_SizeX,sp_SizeX
dc.l PNameSizeY,Pref_SizeY,sp_SizeY
dc.l PNameWinX,Pref_WinX,sp_WinX
dc.l PNameWinY,Pref_WinY,sp_WinY
dc.l PNameZoomX,Pref_ZoomX,sp_ZoomX
dc.l PNameZoomY,Pref_ZoomY,sp_ZoomY
dc.l PNameFont,Pref_Font,sp_Font
dc.l PNameFontSize,Pref_FontSize,sp_FontSize
dc.l 0,0,0 ;end
PNamePub dc.b 'PUBSCREEN',0
PNameCustom dc.b 'CUSTOMSCREEN',0
PNameModeID dc.b 'ModeID',0
PNameSizeX dc.b 'Scr_Width',0
PNameSizeY dc.b 'Scr_Height',0
PNameNotCenter dc.b 'DONOTCENTER',0
PNameNotActivate dc.b 'DONOTACTIVATE',0
PNameWinX dc.b 'Window_Left',0
PNameWinY dc.b 'Window_Top',0
PNameZoomX dc.b 'Paused_Left',0
PNameZoomY dc.b 'Paused_Top',0
PNameLevel dc.b 'Level',0
PNameCusWid dc.b 'CUSTOM_WIDTH',0
PNameCusHei dc.b 'CUSTOM_HEIGHT',0
PNameCusBom dc.b 'CUSTOM_MINES',0
PNameFont dc.b 'Font',0
PNameFontSize dc.b 'FontSize',0
PNamePalette dc.b 'PALETTE',0
PNameGfx dc.b 'GFXTYPE',0
PNameNoQuestion dc.b 'NOQMARK',0
PNameDeadQ dc.b 'QUESTION_DEAD',0
PNameCountD dc.b 'COUNTDOWN',0
PNameNoRMouse dc.b 'NORMOUSEGAME',0
PNameWBLike dc.b 'WBLIKE',0
PNameWarn dc.b 'DONOTWARN',0
PNameIconify dc.b 'ICONIFY',0
PNameScale dc.b 'SCALEGFX',0
TOOLTYPEITEMS = 27
;***Structure Default playfield sizes
even
DefPFSizes dc.l 0,0 ;no data
dc.w EASYWIDTH
dc.w EASYHEIGHT
dc.w EASYBOMBS,0 ;zero just for allign (8)
dc.w MEDIUMWIDTH
dc.w MEDIUMHEIGHT
dc.w MEDIUMBOMBS,0
dc.w HARDWIDTH
dc.w HARDHEIGHT
dc.w HARDBOMBS,0
dc.w PROFIWIDTH
dc.w PROFIHEIGHT
dc.w PROFIBOMBS,0
cpf_Width = 0
cpf_Height = 2
cpf_Bombs = 4
CusPFSizes dc.w MEDIUMWIDTH ;for custom
dc.w MEDIUMHEIGHT
dc.w MEDIUMBOMBS,0
;***Join Hi-Scores data
join_Text dc.b 'Join',0
JoinFilename dcb.b 108,0
JoinGetTitle dc.b 'Select Hi-Score files',0
cnop 0,4
JoinOldDir dc.l 0
JoinDirLock dc.l 0
JoinPrefsBuf dc.l 0
JoinRequester dc.l 0
JoinFileList dc.l 0
SECTION BssVars,BSS
cnop 0,4
Semaphore ds.l 1 ;must not be cleared!
BssStart
IntuiBase ds.l 1
_GfxBase ds.l 1
DosBase ds.l 1
_ReqToolsBase ds.l 1
GadtoolsBase ds.l 1
UtilityBase ds.l 1
MyScreen ds.l 1 ;pointer to the screen used (Workbench or custom)
MyWindow ds.l 1
OldIDCMP ds.l 1 ;IDCMP flags of my window
WinFont ds.l 1 ;screen rastport font
MyFontName ds.b 30
cnop 0,4
SysTime ds.l 2
OldSysTime ds.l 2
MyTime ds.l 2
Ctime ds.l 2 ;current time
EndTime ds.l 2
TimDevBase ds.l 1
StartTime ds.w 2
MenuStruct ds.l 1
TimPort ds.l 1
TimIoReq ds.l 1
RndSeed ds.l 1
Storage ds.l 2 ;just 8 free bytes
OldDirectory ds.l 1
ProgDir ds.l 1
SeedFillStack ds.l 1 ;adr
SeedFillSP ds.l 1 ;ptr at end
MyPrefs ds.l 1 ;ptr to MyPrefs structure
MyDrawInfo ds.l 1
MGGfx ds.l 1 ;ptr to an array of bitmap pointers
PFAdr ds.l 1 ;ptr to play field
PFSize ds.w 1 ;size of play field in bytes
WinCount ds.w 1 ;howmany buttons to press before you win
MaxRandRange ds.w 1
LastXmas ds.w 1
MinRowBut ds.w 1 ;minimum of buttons per row (pf width)
MyBarHeight ds.w 1 ;size of main bar (note MYBARWIDTH is a constant)
winBarH ds.w 1 ;height of the window bar
WinWidth ds.w 1 ;MyWindow size
WinHeight ds.w 1
ZoomWidth ds.w 1
ZoomHeight ds.w 1
WinX ds.w 1 ;MyWindow position
WinY ds.w 1
MinX ds.w 1 ;upper left corner of the inner area
MinY ds.w 1
MinPFX ds.w 1 ;start of the playfield gfx
MinPFY ds.w 1
PFXPix ds.w 1 ;playfield size in pixels
PFYPix ds.w 1
InnWidth ds.w 1 ;size of the inner area
InnHeight ds.w 1
PFWidth ds.w 1 ;Play Field Size (buttons per x/y)
PFHeight ds.w 1
PFBombs ds.w 1
ButtWidth ds.w 1 ;button size
ButtHeight ds.w 1
TimeX ds.w 1 ;position of Time and BCount displays
TimeY ds.w 1
BCountX ds.w 1
BCountY ds.w 1
BCount ds.w 1
CenterPointX ds.w 1
CenterPointY ds.w 1
LastX ds.w 1
LastY ds.w 1
ScreenPalette ds.l PALENTRIES*3+2
gtl_IText ds.b it_SIZEOF
;***Some flags------------------
Play ds.b 1 ;if set: timer, rmbtrap, ...
Win ds.b 1 ;if won then 1
Ready ds.b 1 ;if ready to play
HandleNext ds.b 1 ;handle next selected menu?
IDidTheChange ds.b 1 ;Who changed the window size?
Disable ds.b 1 ;if set, disables drawing to screen and playing.
;You can use menu (to change window size)
DisplayTooBig ds.b 1 ;inform user, that he cannot play (disabled)
Sign ds.b 1 ;sign flag for number converting
TimerGo ds.b 1 ;timer stopped/running
FirstTime ds.b 1
ValidHSText ds.b 1
CPointSet ds.b 1
TestXmas ds.b 1
Pause ds.b 1 ;game paused?
SunPressedOnce ds.b 1
FromIconify ds.b 1
PausedLevel ds.b 1
;------------------------------
LastLevel ds.b 1
cnop 0,4
Allocated ds.l MAXALLOCBLOCKS*2+2
AllocPos ds.l 1
;**********Load/Save file data
lf_filename ds.l 1
lf_fhandle ds.l 1
lf_fileLock ds.l 1
lf_buffer ds.l 1
lf_fileLen ds.l 1
lf_fib ds.b $104 ;File_Info_Block
CurrDate ds.b CD_SIZE
GTNewMenu ds.b MMI_NUMOF*gnm_SIZEOF ;buffer for NewMenu structures
IntuiMessBuf ds.b im_SIZEOF
NameBuffer ds.b NAMELEN
HiScoresText ds.b HS_TEXTMEM
PROGNAMELEN = 32
ProgramName ds.b PROGNAMELEN
WinPortSigBit ds.b 1
PubPortSigBit ds.b 1
cnop 0,4
SignalBits ds.l 1
bitScaleArgs ds.w bsa_SIZEOF/2
cnop 0,4
BssSectionAlign ds.l 1
BssEnd